Professional Documents
Culture Documents
Swing Data Binding: Karsten Lentzsch
Swing Data Binding: Karsten Lentzsch
Karsten Lentzsch
www.JGoodies.com
Presentation Goals
Understand MVC and Swing models.
Learn how to bind domain objects
to Swing UI components.
Speaker Qualifications
Agenda
Introduction
MVC and Swing
How to bind single values?
How to bind lists
A 3-tier Swing architecture
How binding works in projects
Utils
Application 2
Help
Printing
Layout
Binding
JRE / Swing
Validation
Applications
Helper Code/Libs
Application Frame
Basic Libraries
Foundation
Utils
Application 2
Help
Printing
Layout
Binding
JRE / Swing
Validation
Applications
Helper Code/Libs
Application Frame
Basic Libraries
Foundation
Questions
I - Basics
MVC and Swing
Before MVC
Painting Code
State Operations
(Control Behavior)
State
Client
State
Server
:: JGOODIES :: Java User Interface Design
State Modifications
State
Domain Layer
Loose Coupling
The domain shall not reference the GUI
Presentation refers to domain and can
modify it
Advantages:
Reduces complexity
Allows to build multiple presentations
of a single domain object
:: JGOODIES :: Java User Interface Design
Loose Coupling
Painting Code
State Modifications
reports changes
refers to/modifies
State
MVC
refers to
View
Controller
changes
reports
Model
MVC
refers to
View
Controller
changes
reports
Model
Controller
GUI Model
Domain Model
Presentation Layer
Domain Layer
:: JGOODIES :: Java User Interface Design
Presentation Layer
C
M
Model Layer
M
Domain Object
DO
DO
Domain Layer
:: JGOODIES :: Java User Interface Design
M-JComponent-VC
View
JComponent
Controller
Swing Model(s)
Example: JCheckBox
Painting
JCheckBox
Event
Handling
MetalCheckBoxUI
ToggleButtonModel
BasicButtonUI
Painting
MouseListener
Event
Handling
MouseMotionListener
MetalCheckBoxUI
ToggleButtonModel
FocusListener
PropertyChangeListener
ChangeListener
GUI Properties
ToggleButtonModel
armed
pressed, ...
GUI State
selected
Data State
GUI Component
ToggleButtonModel
selected
anAlbum
title=Preludes
classical=true
Data Model
Domain object
:: JGOODIES :: Java User Interface Design
GUI Component
aToggleButtonModel
selected=true
anAlbum
title=Preludes
classical=true
Data Model
connect,
synchronize
Domain Object
:: JGOODIES :: Java User Interface Design
Summary
II - Binding Values
How to connect
domain objects with UI components?
Binding Tasks
aJCheckBox
2. Write
aToggleButtonModel
selected=false
1. Read
#isClassical
anAlbum
title=Preludes
classical=true
:: JGOODIES :: Java User Interface Design
aToggleButtonModel
3. Value changed
selected=true
anAlbum
title=Preludes
classical=true
:: JGOODIES :: Java User Interface Design
aJCheckBox
1. Read
aToggleButtonModel
selected=true
anAlbum
title=Preludes
classical=false
2. Write
#setClassical
aToggleButtonModel
selected=true
anAlbum
title=Preludes
classical=true
3. Value changed
Alternative
aJCheckBox
aToggleButtonModel
selected=false
anAlbum
title=Preludes
classical=true
Note: you can't share the model
implements
TableModel
myAlbumTableAdapter
implements
anAlbumClassicalToggleButtonAdapter
ToggleButtonModel
Converts Album#classical
to ToggleButtonModel
anAlbum
title=Preludes
classical=true
:: JGOODIES :: Java User Interface Design
Concept
Use a universal model (ValueModel)
Convert domain properties to ValueModel
Build converters from ValueModel
to Swing models: ToggleButtonModel, etc.
We end up with about 15 classes.
aToggleButtonAdapter
aValueModel
anAlbum
title=Preludes
classical=true
:: JGOODIES :: Java User Interface Design
ValueModel: Requirements
We want to get its value
We want to set its value
We want to observe changes
aToggleButtonAdapter
aPropertyAdapter
propertyName=classical
implements
implements
ToggleButtonModel
ValueModel
anAlbum
title=Preludes
classical=true
:: JGOODIES :: Java User Interface Design
PropertyAdapter
BeanAdapter and PropertyAdapter
convert Bean properties to ValueModel
Observe bound properties
Use Bean Introspection that in turn uses
Reflection to get and set bean properties
aToggleButtonAdapter
aPropertyAdapter
propertyName=classical
anAlbum (Bean)
title=Preludes
classical=true
ValueModel
implements
get/set
ComponentFactory
private void initComponents() {
Album album = getEditedAlbum();
JCheckBox classicalBox =
ComponentFactory.createCheckBox(
album,
Album.PROPERTYNAME_CLASSICAL);
}
BufferedValueModel
aJCheckBox
aBufferedValueModel
aTriggerChannel
implements
ValueModel
aPropertyAdapter
implements
anAlbum
classical=true
:: JGOODIES :: Java User Interface Design
aJTextField
aToggleButtonAdapter
aDocumentAdapter
aBufferedValueModel
aTriggerChannel
aPropertyAdapter
aBufferedValueModel
aPropertyAdapter
anAlbum
title=Preludes
classical=true
:: JGOODIES :: Java User Interface Design
aJFormattedTextField
aDocumentAdapter
aPropertyConnector
aPropertyAdapter
for Album#title
aPropertyAdapter
for Album#releaseDate
anAlbum
title=Preludes
releaseDate=Dec-5-1967
:: JGOODIES :: Java User Interface Design
aJTextField
aJFormattedTextField
Formatter
aDocumentAdapter
aPropertyConnector
DateToStringConverter
aPropertyAdapter
for Album#releaseDate
aPropertyAdapter
for Album#releaseDate
anAlbum
releaseDate=Dec-5-1967
:: JGOODIES :: Java User Interface Design
Indirection
aJCheckBox
aJTextField
aToggleButtonAdapter
aDocumentAdapter
aPropertyAdapter
propertyName=classical
aPropertyAdapter
propertyName=title
Holds the
edited album
aBeanChannel
anAlbum
title=Preludes
classical=true
anAlbum
title=Etudes
classical=true
:: JGOODIES :: Java User Interface Design
Indirection
aJCheckBox
aJTextField
aToggleButtonAdapter
aDocumentAdapter
aPropertyAdapter
propertyName=classical
aPropertyAdapter
propertyName=title
Holds the
edited album
aBeanChannel
anAlbum
title=Preludes
classical=true
anAlbum
title=Etudes
classical=true
:: JGOODIES :: Java User Interface Design
ListModel Implementations
ArrayListModel extends ArrayList,
implements ListModel
LinkedListModel extends LinkedList,
implements ListModel
We can operate on List and
can observe ListModel changes.
:: JGOODIES :: Java User Interface Design
ListModel
anArrayListModel
implements
List
aBook
aBook
anAlbum
:: JGOODIES :: Java User Interface Design
anAlbumTableAdapter
implements
TableModel
ListModel
anArrayListModel
implements
List
aBook
aBook
anAlbum
:: JGOODIES :: Java User Interface Design
SelectionInList
aJList
SelectionAdapter
aSelectionInList
ListModel
SelectionHolder
aBook
aBook
anAlbum
:: JGOODIES :: Java User Interface Design
Overview / Detail
aJTextField
aJList
SelectionAdapter
aSelectionInList
ListModel
aDocumentAdapter
aPropertyAdapter
propertyName=title
SelectionHolder
beanChannel
aBook
aBook
anAlbum
:: JGOODIES :: Java User Interface Design
IV - Architecture
A 3-tier Swing client architecture
Design Goals
Works with standard Swing components
Works with custom Swing components
Requires no special components
Requires no special panels
Integrates well with validation
Works with different validation styles
:: JGOODIES :: Java User Interface Design
JButton
ListModel
Action
JTextField
ValueModel
Presentation
Model Layer
Domain Object
Domain Layer
DO
DO
:: JGOODIES :: Java User Interface Design
Benefit of 3 Layers
Multiple Views
View 1
View 2
JTextField
JMenuItem
JButton
JLabel
Presentation
JList
ListModel
Action
ValueModel
Model Layer
ButtonActionPropertyChangeListener
ListModel
Action
ValueModel
#enabled
Setting UI Properties
View
JTextField
ModelChangeHandler
JButton
JList
GUI Model
ValueModel
Can provide
bound bean properties
JTextField
BeanAdapter
Album
#title
#artist
#classical
JCheckBox
Presentation
Vends PropertyAdapters
Domain Layer
titleField;
classicalBox;
buyNowButton;
referencesList;
cc.xy(1,
cc.xy(3,
cc.xy(3,
cc.xy(3,
cc.xy(3,
1));
1));
3));
5));
7));
return builder.getPanel();
}
:: JGOODIES :: Java User Interface Design
*/
V - Field Report
How does Adapter Binding work?
Costs
Adapter Binding:
increases learning costs
decreases production costs a little
can significantly reduce change costs
Use a ComponentFactory!
Encapsulate the creation of adapters from
ValueModel to Swing components.
Some components have no appropriate
model, e. g. JFormattedTextField
Vends components for ValueModels
:: JGOODIES :: Java User Interface Design
Buffering
Use BufferedValueModel judicously
prevents validation on domain models
makes it harder to use domain logic
Performance
Adapter chains fire many change events
That seems to be no performance problem
ListModel can improve the performance
compared to copying list contents
Debugging
Copying approach is easy to debug;
you can see when where what happens.
Adapter chains move values implicitly;
it's harder to understand updates.
Reflection and Introspection hide
who reads and writes values.
Favor named over anonymous listeners.
Renaming Methods
Reflection and Introspection make it
more difficult to rename bean properties
and their getter and setters.
Use constants for bean property names!
Obfuscators fail to detect the call graph.
:: JGOODIES :: Java User Interface Design
End
Summary and References
Summary
Example 2
Example n
Applications
Convenience Sources
Helper Code
Framework
Looks
Forms
Binding
JRE / Swing
Validation
Basic Libraries
Foundation
References I
Fowler's Enterprise Patterns
martinfowler.com/eaaDev/
JGoodies Binding
binding.dev.java.net
JGoodies Articles
www.JGoodies.com/articles/
JGoodies Demos
www.JGoodies.com/freeware/
:: JGOODIES :: Java User Interface Design
References II
Sun's JDNC
jdnc.dev.java.net
Understanding and Using ValueModels
c2.com/ppr/vmodels.html
Oracle's JClient and ADF
otn.oracle.com/, search for 'JClient'
Spring Rich Client Project
www.springframework.org/spring-rcp.html
:: JGOODIES :: Java User Interface Design
Demo/Tutorial:
End
Good Luck!
Karsten Lentzsch