Date post: | 03-Apr-2018 |
Category: |
Documents |
Upload: | macadoshis |
View: | 218 times |
Download: | 0 times |
of 21
7/28/2019 GUIPatterns ZK Java Article Final
1/21
Implementing event-driven GUI patterns using the ZK
Java AJAX framework
Simon Massey ([email protected])Sachin K Mahajan ([email protected]), IBM
August 2012
Copyright International Business Machines Corporation 2012. All rights reserved.
Summary: This white paper explores three event-driven graphical user interface (GUI) patterns
using the ZK Java AJAX framework; specifically, "Passive View", "Supervising Controller" and"Presentation Model". The patterns are discussed in the context of a simple screen implemented
three times using each of the three patterns.
Table of Contents
1 Introduction...................................................................................................................................11.1 Rich client GUI patterns.........................................................................................................2
1.2 ZK Event-driven programming..............................................................................................2
2 Example UI....................................................................................................................................3
3 Implementing the Passive View....................................................................................................4
4 Implementing the Presentation Model..........................................................................................85 Implementing the Supervising Controller...................................................................................13
6 Comparing the patterns...............................................................................................................187 Conclusion...................................................................................................................................19
8 Resources.....................................................................................................................................20
9 About the authors........................................................................................................................20
1 IntroductionZK is a rich Internet application (RIA) framework that invokes JavaTM event handlers running at
the server in response to Document Object Model (DOM) events from the browser. This allowsan application developer to choose rich graphical user interface (GUI) patterns that are normally
applied within desktop programming environments.
1
mailto:[email protected]:[email protected]:[email protected]:[email protected]:[email protected]:[email protected]7/28/2019 GUIPatterns ZK Java Article Final
2/21
In this paper, we explore three event-driven GUI patterns using the ZK framework: Passive
View, Supervising Controller, and Presentation Model, presenting the patterns in the context of a
simple screen implemented three times, using the approach outlined by each pattern.
1.1 Rich client GUI patterns
GUI patterns address the subject of how to organize code to make best use of GUI frameworks.ZK has an asynchronous, stateful, event-driven programming model known as a "rich client
system". In this paper we contrast three rich client GUI architectural patterns as described in the
document, Development of Further Patterns of Enterprise Application Architecture, by MartinFowler.
Passive View. A screen of components with all application-specific behavior extracted into adominant controller such that the GUI widgets have their state controlled entirely by the
controller.
Presentation Model. Represents the state and behavior of the presentation independently of
the GUI widgets used within the interface.
Supervising Controller. Factors the UI into a view and a controller, in which the viewhandles simple mapping to the underlying model and the controller handles the input
response and complex view logic.
It should be noted that each approach has its own opportunities and challenges. The optimal
approach depends on the context of the application; that is, both the organization of the screens
and of the business logic.
1.2 ZK Event-driven programming
ZK is an event-driven, component-based framework that gives the illusion of painting the server-side "Desktop" of Java GUI widgets as HTML into the browser screen. This makes it easier towrite complex data-driven GUIs using a Java rich-client GUI API on the server. In this section
we provide an overview of the framework runtime that archives this effect.
Figure 1 is taken from the ZK Developer Guide and shows an outline of a running ZK
application. A browser request causes the ZK Loader to render ZUML (ZUL/XHTML) pages as
a desktop of Java GUI widget (Components) that are held within the user's HTTP session.
This desktop of server-side Java components is rendered to the browser as DHTML. Browser
DOM events are dispatched by the ZK Client Engine (JavaScript/jQuery) over AJAX to the ZK
Asynchronous Update (AU) Engine (Java/Servlet). The ZK AU Engine then runs the server-sideevent handler of the corresponding Java GUI Component.
2
http://martinfowler.com/eaaDev/http://martinfowler.com/eaaDev/7/28/2019 GUIPatterns ZK Java Article Final
3/21
Figure 1. The ZK Client and Update engine
Server-side Java event handlers attached to the desktop components then invoke the application
business logic. Any modifications to the Java GUI Widgets made by the application eventhandlers are asynchronously returned to the browser in the AJAX response. The ZK Client
Engine dynamically redraws the corresponding parts of the browser DOM in response to the
asynchronous update.
ZK provides a data-binding framework, "ZK Bind," which removes the necessity of writing
boilerplate code to move data between screen state (the GUI Widgets) and session state (theunsaved business entities). Attributes within the page configure the data-binding of the screen
components onto server-side object properties. Attributes may also configure 'commandbindings'
of screen event handlers onto server-side object methods.
This capability allows developers to choose between the full gambit of Model-View-Presenter
(MVP), Model-View-Controller (MVC), Model-View-ViewModel (MVVM), and (Model-View-
ViewModel-Presenter (MVVMP) patterns.
2 Example UIThe example user interface is the simple Create, Revise, Update, and Delete (CRUD) screen
backed by a single database table, as shown in figure 2.
3
7/28/2019 GUIPatterns ZK Java Article Final
4/21
Figure 2. ZK Todo - Application Model screen
The sample code accompanying this paper is available on Github,the public sourcecontrol
server, under the Apache2 open-source license. (All links to files point to the sourcecontrol
server, which has instructions to check out and build from sourcecontrol.)
The code has the same screen implemented three times using the three GUI patterns. The simple
backend of the screen is a Java Persistence Architecture (JPA) entity and a transactional servicefor performing persistence operations.
A detailed walk-through of the ZK features used in these screens is given in a near identical
example within the official ZK documentation. The reader is encouraged to refer to thatdocumented example to supplement the descriptions below.
3 Implementing the Passive ViewThe Passive View implementation is shown within the filepassiveview.zuland the
accompanying Presenter.java class. The name of the Java class refers to the pattern moniker'Model-View-Presenter (MVP)'. Figure 3 shows the entire ZUL screen.
Figure 3. passiveview.zul
1 :
2 :
3 :
4 :
4
https://github.com/simbo1905/ZkToDo2https://github.com/simbo1905/ZkToDo2http://books.zkoss.org/wiki/ZK_Getting_Started/Creating_a_Database-driven_Applicationhttp://books.zkoss.org/wiki/ZK_Getting_Started/Creating_a_Database-driven_Applicationhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/passiveview.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/passiveview.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/ui/Presenter.javahttp://books.zkoss.org/wiki/ZK_Getting_Started/Creating_a_Database-driven_Applicationhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/passiveview.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/ui/Presenter.javahttps://github.com/simbo1905/ZkToDo27/28/2019 GUIPatterns ZK Java Article Final
5/21
5 :
6 :
7 :
8 :
9 :
10 :
11 :
12 :
13 :
14 : Item:
15 : Priority:
16 : Date:
17 :
18 :
19 :
20 :
21 :
22 :
23 :
24 :
Figure 3 above provides only the static layout of the screen; neither display logic nor data-
bindings are configured within the markup. The application logic is added into the page by the
"apply" attribute in line 4.
This names the Presenter class (see figure 4) as the composer for this screen. Annotations within
the Java class automatically wire screen components and event handlers into the Presenter object.
Figure 4. Extracts from Presenter.java 1:package org.zkforge.zktodo2.ui;
34:@VariableResolver(org.zkoss.zkplus.spring.DelegatingVariableResolver.class)
35:publicclassPresenterextendsSelectorComposerimplements
5
7/28/2019 GUIPatterns ZK Java Article Final
6/21
36: ListitemRenderer{
40: // auto-wired property
41: @WireVariableReminderService reminderService;
42:
43: // components
44: @WireTextbox name;
45: @WireIntbox priority;
46: @WireDatebox date;
47: @WireListbox list;
48:
49: // conversation state
50: ListModelList listModelList;
51: Reminder selectedReminder =newReminder();
52:
53: @Override
54: publicvoid doAfterCompose(Window comp)throwsException{
55: super.doAfterCompose(comp);// super method wires thecomponents
56: // load the data and bind to the list then set self as list
renderer
57: listModelList =newListModelList();
58: List reminders = reminderService.findAll();
59: listModelList.addAll(reminders);
60: list.setModel(listModelList);
61: list.setItemRenderer(this);
62: }
63:
64: @Listen("onSelect = #list")
65: publicvoidselect(SelectEvent e){
66: selectedReminder = e.getSelectedObjects().iterator().next();
67: date.setValue(selectedReminder.getDate());
68: priority.setValue(selectedReminder.getPriority());
6
7/28/2019 GUIPatterns ZK Java Article Final
7/21
69: name.setValue(selectedReminder.getName());
70: return;
71: }
72:
73: @Listen("onClick = #add")
74: publicvoid add(Event e){
75: Date dateValue = date.getValue();
76: Integer priorityValue = priority.getValue();
77: String nameValue = name.getValue();
78: if( dateValue !=null&& priorityValue !=null&& nameValue !=null){
79: Reminder reminder =newReminder();
80: reminder.setDate(date.getValue());
81: reminder.setName(name.getValue());
82: reminder.setPriority(priority.getValue());
83: this.reminderService.persist(reminder);
84: List reminders =this.reminderService.findAll();
85: this.listModelList.clear();
86: this.listModelList.addAll(reminders);
87: this.selectedReminder = reminder;
88: }
89: }
90:
91: @Listen("onClick = #update")
92: publicvoid update(Event e){
93: if( selectedReminder !=null){
116: }
117: }
118:
119: @Listen("onClick = #delete")
120: publicvoiddelete(Event e){
7
7/28/2019 GUIPatterns ZK Java Article Final
8/21
142: }
143:
144: protectedSimpleDateFormat dateFormat =newSimpleDateFormat("dd-MMM-
yy");
145:
146: @Override
147: publicvoid render(Listitem listItem,Reminder reminder,int index)throwsException{
148: newListcell(reminder.getName()).setParent(listItem);
149: newListcell(reminder.getPriority()+"").setParent(listItem);
150: newListcell(dateFormat.format(reminder.getDate())).setParent(listItem);
151: }
152:
153:}
In figure 4 the @VariableResolver (line 34) and @WireVariable (line 41) cause the domainservices to be obtained from Spring. The @Wire annotations (lines 44 -- 47) cause the screen
GUI Components defined by the ZUL file to be injected. The @Listen annotations on the
methods specify selectors to bind the Java methods onto the GUI widget event handlers.
The Presenter class is a GUI-heavy class that implements ListitemRenderer and supplies theListbox rendering method at line 147. The doAfterCompose method (line 54) populates thescreen after it has been initialized by loading the entities from the service (line 58).
It then sets itself as the render of the list model (line 61). Such details are absent from the other
examples that offload such work to the framework Binder, which is configured by additionalmarkup within the page.
4 Implementing the Presentation ModelThe Presentation Model implementation is shown within the filepresentationmodel.zul and the
accompanying ViewModel.java class. The name of the Java refers to the moniker 'Model-View-
View-Model (MVVM)'. Figure 5 shows the entire ZUL file.
Figure 5. presentationmodel.zul
1 :
2 :
3 :
8
https://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/presentationmodel.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/presentationmodel.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/ui/ViewModel.javahttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/presentationmodel.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/ui/ViewModel.java7/28/2019 GUIPatterns ZK Java Article Final
9/21
4 :
8 :
11 :
12 :
13 :
14 :
15 :
16 :
17 :
18 :
19 :
20 :
21 :
22 :
23 :
24 :
26 :
27 : Item:
28 :
30 : Priority:
31 :
7/28/2019 GUIPatterns ZK Java Article Final
10/21
32 : value="@bind(r.priority)"/>
33 : Date:
34 :
36 :
37 :
38 :
40 :
42 :
44 :
45 :
46 :
47 :
49 :
50 :
51 :
52 :
At line 5 of figure 5, the framework BindComposer is applied to the screen. This introduces data
bindings and command bindings to map both screen state and screen events onto the server-side
objects. The bindings are in the form of EL expressions within '@annotation' attributes. Forexample, lines 18 -- 20 have XML @load attributes that load the name, priority, and date of the
Reminder objects into Listcell components.
At line 6 an instance of the ViewModel class is assigned to the viewModel attribute of the
window. This sets it as the target of the @command bindings which maps the button onClick
10
7/28/2019 GUIPatterns ZK Java Article Final
11/21
event handles to server-side methods (Java lines 39, 41, and 43). The ViewModel object is
assigned the EL variable name 'vm'. Figure 6 shows extracts from the ViewModel java class.
Figure 6. ViewModel.java
1:package org.zkforge.zktodo2.ui;
13:@VariableResolver(org.zkoss.zkplus.spring.DelegatingVariableResolver.class)//wire with Spring
14:publicclassViewModel {
15:
16: // auto-wired property
17: @WireVariableReminderService reminderService =null;
27: protectedList reminders =newArrayList();
28:
29: publicList getReminders(){
30: List rs =this.reminderService.findAll();
31: this.reminders.clear();
32: this.reminders.addAll(rs);
33: returnthis.reminders;
34: }
35:
36: protectedReminder selectedReminder =newReminder();
47: @Command
48: @NotifyChange({"reminders","selectedReminder"})
49: publicvoiddelete(){
50: if(this.selectedReminder.getId()!=null){
51: try{
52: this.reminderService.delete(selectedReminder);
53: this.selectedReminder =newReminder();
54: }catch(Exception e){
55: e.printStackTrace();
11
7/28/2019 GUIPatterns ZK Java Article Final
12/21
56: }
57: }
58: }
59:
60: @Command
61: @NotifyChange({"reminders","selectedReminder"})
62: publicvoid save(){
63: if(this.selectedReminder.getId()!=null){
64: try{
65: this.reminderService.persist(selectedReminder);
66: }catch(Exception e){
67: e.printStackTrace();
68: }
69: }else{
70: this.reminderService.persist(this.selectedReminder);
71: }
72: }
73:
74: @Command
75: @NotifyChange({"reminders","selectedReminder"})
76: publicvoid create(){
77: this.selectedReminder =newReminder();
78: }
79:
80:}
Annotations within the Java class initialize the ViewModel object. The @VariableResolver (line13) and @WireVariable (line 17) annotations cause the domain services to be obtained from
Spring. The @Command annotations on the Java methods mark them as commandbinding
methods for the framework binder.
The @NotifyChange annotations on the Java methods indicate which state will be updated in
response to commands. This indicates to the binder which properties should be reloaded into thescreen after executing commands.
12
7/28/2019 GUIPatterns ZK Java Article Final
13/21
The ViewModel class does not have references to GUI widgets nor GUI events. Its responsibility
is to be the screen-independent model of the users interaction with the application, and it holdsthe session state in the properties 'reminders' (line 27) and 'selectedReminder' (line 36).
The ViewModel is the mediator of the domain service reminderService (line 17). An instanceof the ViewModel is the target of the screen data-bindings, that is, what we call the "bindmodel".
The salient feature of the Presentation Model example is that the ViewModel is active andmediates the business services. The client of the ViewModel is the framework Binder that
updates the GUI widgets, and the user is interacting with the active bindmodel through screens
animated by the framework Binder.
5 Implementing the Supervising ControllerThe Supervising Controller approach is shown within the file supervisingcontroller.zul, the
accompanying Controller.java and Model.javaclasses. The names of the Java class refer to the
pattern moniker 'Model-View-Controller (MVC)'. Figure 7 shows the Supervising ControllerZUL file.
Figure 7. Supervising Controller
1 :
2 :
3 :
4 :
8 :
11 :
12 :
13 :
14 :
15 :
16 :
13
https://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/supervisingcontroller.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/ui/Controller.javahttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/Model.javahttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/Model.javahttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/webapp/supervisingcontroller.zulhttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/ui/Controller.javahttps://github.com/simbo1905/ZkToDo2/blob/developerworks/src/main/java/org/zkforge/zktodo2/Model.java7/28/2019 GUIPatterns ZK Java Article Final
14/21
17 :
18 :
19 :
20 :
21 :
22 :
23 :
24 :
26 :
27 : Item:
28 : Priority:
29 : Date:
30 :
31 :
32 :
33 :
34 :
35 :
36 :
37 :
38 :
39 :
40 :
14
7/28/2019 GUIPatterns ZK Java Article Final
15/21
41 :
42 :
At line 5 the framework BindComposer is applied to the screen, and at line 6 an instance of the
Controller is made the target of the framework Binder. Much of the ZUL file is similar to thePresentation Model screen using databindings and commandbindings.
The main difference is in the organization of the Java code. The Controller object has a property,
'controller.model,' that is referenced in the databindings throughout the page. This property is an
instance of class Model that represents the users session state with the application businesslogic. Figure 8 shows extracts from the Model class.
Figure 8. Model.java
1:package org.zkforge.zktodo2;
10:@Scope("desktop")
11:@Named("model")
12:publicclassModel{
18: protectedReminder selectedReminder =newReminder();
19:
20: publicReminder getSelectedReminder(){
21: returnthis.selectedReminder;
22: }
23:
24: publicvoid setSelectedReminder(Reminder reminder){
25: this.selectedReminder = reminder;
26: }
27:
28: privateList reminders =newArrayList();
29:
30: publicList getReminders(){
31: returnthis.reminders;
32: }
33:}
15
7/28/2019 GUIPatterns ZK Java Article Final
16/21
The model is a simple bean holding the screen data in the properties, 'selectedReminder' (line 18)
and 'reminders' (line 28). At line 10 the spring bean is given "Desktop" scope, binding the users
application session state to the current ZK Desktop. Figure 9 shows extracts of the Controllerclass.
Figure 9. Controller class 30:@VariableResolver(org.zkoss.zkplus.spring.DelegatingVariableResolver.class)//wire with Spring
31:publicclassController{
32:
33: // wired components
34: @WireTextbox name;
35: @WireIntbox priority;
36: @WireDatebox date;
37: @WireListbox list;
38:
39: // wired property
40: @WireVariableModel model =null;
50: // wired property
51: @WireVariableReminderService reminderService =null;
61: @Init
62: publicvoid init(@ContextParam(ContextType.VIEW)Component view){
63: Selectors.wireComponents(view,this,false);
64: reload();
65: }
66:
67: protectedvoid reload(){
68: List reminders =this.reminderService.findAll();
69: this.model.getReminders().clear();
70: this.model.getReminders().addAll(reminders);
71: }
16
7/28/2019 GUIPatterns ZK Java Article Final
17/21
76: @Command
77: publicvoid create(@ContextParam(ContextType.TRIGGER_EVENT)Event e){
78: Date dateValue = date.getValue();
79: Integer priorityValue = priority.getValue();
80: String nameValue = name.getValue();
81: if( dateValue !=null&& priorityValue !=null&& nameValue !=null){
82: Reminder reminder =newReminder(nameValue,priorityValue, dateValue);
83: this.reminderService.persist(reminder);
84: this.model.setSelectedReminder(reminder);
85: reload();
86: }
87: return;
88: }
93: @Command
94: publicvoid save(@ContextParam(ContextType.TRIGGER_EVENT)Event e){
95: Reminder selectedReminder =this.model.getSelectedReminder();
96: if( selectedReminder !=null){
97: try{
98: this.reminderService.persist(selectedReminder);
99: }catch(Exception exception){
100: // not implemented
101: }
102: reload();
103: }
104: }
109: @Command
110: publicvoiddelete(@ContextParam(ContextType.TRIGGER_EVENT)Event e){
17
7/28/2019 GUIPatterns ZK Java Article Final
18/21
121: }
122:
123:}
The controller is given an instance of the model bean (line 40) and the business service (line 51).Within the ZUL file, 'controller.model,' is the target of the databindings, that is, the bindmodel.
Within the methods, the controller mediates the services and updates the bindmodel.
The salient feature of this implementation is the segregation of UI event processing and
application conversational state. The responsibility of the controller object is to respond to screen
events, and the responsibility of the model is to represent the business state displayed on thescreen.
Within the sample code the Model object is passive and has no references to the businessservices. The Controller mediates the business services and "pushes" entities into the passive
bindmodel. An alternative approach is to have the Model class have the references to the servicesrather than the Controller class. Then the Controller could "pull" entities through methods of anactive bindmodel.
6 Comparing the patternsPassive ViewThe imperative rather than declarative nature of the Presenter within the Passive View example is
both its strength and its weakness. The display logic is quite explicit, making debugging simple.By explicitly handing all the display logic, the code has fine-grained control; however, it is
verbose and screen specific and requires developer discipline to keep screen logic separated from
the business logic.
Such fine-grained control of display logic is useful for creating re-usable screen fragments. As
such, it is compatible with the other approaches to building macro-widgets and standardizeddialogue screens. Large-scale screen presenters may be brittle, as late feedback to the layout and
organization of a screen could force a significant rewrite. JUnit testing of custom screen logic can
be also brittle and tedious.
Presentation ModelThe declarative nature of the screen within the Presentation Model is both its strength and
weakness. The display logic is offloaded to the framework binder by use of the observer pattern.
This may make debugging screen update problems difficult and can lead to excessive observerupdates if care is not taken.
On the other hand, rendering is configured rather than programmed, which should reduce
development time. The absence of custom display code should make JUnit tests less brittle.
18
7/28/2019 GUIPatterns ZK Java Article Final
19/21
The absence of GUI Widget references and GUI Events within ViewModel class used with
Presentation Model encourages a clear segregation of display logic from business logic. This
requires expertise in configuring the framework Binder to drive the screen by observing theViewModel.
In return for this investment, different screens may be used to "skin" a ViewModel. A "ZKTouch" screen (jQuery Mobile) can render the ViewModel for a phone in addition to regular
pages rendering the same ViewModel for a traditional mouse-driven screen.
Supervising ControllerThe flexibility of the Supervising Controller approach is both its strength and weakness in that a
blend of the two other approaches can be taken. Databinding can be supplemented by direct GUIWidget updates from the controller as seen in the Passive View example.
The model to which the screen is bound can be a passive bindmodel (state only) or have methodsthat mediate business services like the Presentation Model example. It may aim to get the better
of the other two approaches but, without care, may achieve only their combined weaknesses.
The segregation of UI action processing from business session state seen in the SupervisingController approach is a traditional Web application approach. Yet separation of state and
behavior can lead to brittle procedural logic rather than a supple object model. Business logic
easily bleeds into procedural controllers, making maintenance and reuse harder.
On the other hand, if the business logic is procedural or external in nature, then the logic will
naturally fall into a controller that mediates the business methods, which then pushes the resultsinto a passive bindmodel.
7 ConclusionThis article has presented an overview of the implementation of three rich client GUI patterns
using ZK. The definition of the patterns given by Martin Fowler provide a clear statement of
intent; they are strategies to organize rich GUI code.
An architectural pattern is an abstract concept; any implementation is an interpretation of an
outline. The implementation has a context (framework, existing code, skills, requirements,process) that moderates the approach.
The sample screen presented in this paper is trivial in nature, and it would be ill advised to
extrapolate the simple implementations presented here to a full-scale system. Instead, the
examples serve only to encourage discussion as to the paths open to developers when using theZK Framework; they are not a map, but a suggestion of possible routes.
To ask the question "Which is the best strategy?" is like asking the question "Who is first among
equals?". Each pattern is an outline approach that has emerged in a response to real world
experiences; as such, they are each distilled wisdom.
19
7/28/2019 GUIPatterns ZK Java Article Final
20/21
8 Resources The ZkToDo2 project, which is the sample code for this article:
https://github.com/simbo1905/ZkToDo2
developerWorks article, Rich Internet applications using ZK:
http://www.ibm.com/developerworks/web/library/wa-aj-open/?S_TACT=105AGX08&S_CMP=HP
developerWorks article, Enhance Ajax development with a fusion of jQuery, ZK, and Java
code;http://www.ibm.com/developerworks/web/library/wa-aj-zkquery/
developerWorks WebSphere Portal zone:http://www.ibm.com/developerworks/websphere/zones/portal/
Free ZK download:http://www.zkoss.org/download/zk.dsp
ZK MVC:http://books.zkoss.org/wiki/Small_Talks/2008/August/ZK_MVC_Made_Easy
ZK Developer's Reference/MVVM/Data Binding:
http://books.zkoss.org/wiki/ZK_Developer%27s_Reference/MVVM/Data_Binding
9 About the authors
Simon Massey is a Technical Architect working for a bank holding company in London and hasbuilt several large-scale systems using ZK since 2007. He is a founding member and speaker at
the ZK UK User Group, has published a number of ZK articles, and currently maintains the
ZkToDo2 ZK Patterns Sample application. You can reach him [email protected].
Sachin K Mahajan currently works on the Development team of the Unica product, which is part
of the Enterprise Marketing Management group of IBM Software Group. He graduated with a
20
https://github.com/simbo1905/ZkToDo2https://github.com/simbo1905/ZkToDo2http://www.ibm.com/developerworks/web/library/wa-aj-open/?S_TACT=105AGX08&S_CMP=HPhttp://www.ibm.com/developerworks/web/library/wa-aj-open/?S_TACT=105AGX08&S_CMP=HPhttp://www.ibm.com/developerworks/web/library/wa-aj-zkquery/http://www.ibm.com/developerworks/web/library/wa-aj-zkquery/http://www.ibm.com/developerworks/websphere/zones/portal/http://www.zkoss.org/download/zk.dsphttp://docs.zkoss.org/wiki/ZK_MVC_Made_Easyhttp://docs.zkoss.org/wiki/Data_bindingmailto:[email protected]:[email protected]://www.ibm.com/developerworks/web/library/wa-aj-zkquery/http://docs.zkoss.org/wiki/ZK_MVC_Made_Easyhttps://github.com/simbo1905/ZkToDo2http://www.ibm.com/developerworks/web/library/wa-aj-open/?S_TACT=105AGX08&S_CMP=HPhttp://www.ibm.com/developerworks/web/library/wa-aj-open/?S_TACT=105AGX08&S_CMP=HPhttp://www.ibm.com/developerworks/websphere/zones/portal/http://www.zkoss.org/download/zk.dsphttp://docs.zkoss.org/wiki/Data_binding7/28/2019 GUIPatterns ZK Java Article Final
21/21
Masters degree from University of Utah, USA. You can reach him at
Trademarks developerWorks, IBM, WebSphere are trademarks or registered trademarks of IBM
Corporation in the United States, other countries, or both.
Java and all Java-based trademarks and logos are trademarks or registered trademarks of
Oracle, in the United States, other countries, or both.
Other company, product, and service names may be trademarks or service marks of others.
21
mailto:[email protected]:[email protected]