summaryrefslogtreecommitdiffstats
path: root/documentation/jpacontainer/jpacontainer-fieldfactory.asciidoc
diff options
context:
space:
mode:
Diffstat (limited to 'documentation/jpacontainer/jpacontainer-fieldfactory.asciidoc')
-rw-r--r--documentation/jpacontainer/jpacontainer-fieldfactory.asciidoc162
1 files changed, 162 insertions, 0 deletions
diff --git a/documentation/jpacontainer/jpacontainer-fieldfactory.asciidoc b/documentation/jpacontainer/jpacontainer-fieldfactory.asciidoc
new file mode 100644
index 0000000000..f8b6eebac3
--- /dev/null
+++ b/documentation/jpacontainer/jpacontainer-fieldfactory.asciidoc
@@ -0,0 +1,162 @@
+---
+title: Automatic Form Generation
+order: 8
+layout: page
+---
+
+[[jpacontainer.fieldfactory]]
+= Automatic Form Generation
+
+The JPAContainer [classname]#FieldFactory# is an implementation of the
+[interfacename]#FormFieldFactory# and [interfacename]#TableFieldFactory#
+interfaces that can generate fields based on JPA annotations in a POJO. It goes
+further than the [classname]#DefaultFieldFactory#, which only creates simple
+fields for the basic data types. This way, you can easily create forms to input
+entities or enable editing in tables.
+
+The generated defaults are as follows:
+
+[options="header"]
+|===============
+|Annotation|Class Mapping
+|[literal]#++@ManyToOne++#|[classname]#NativeSelect#
+|[literal]#++@OneToOne++#, [literal]#++@Embedded++#|Nested [classname]#Form#
+|[literal]#++@OneToMany++#, [literal]#++@ElementCollection++#|[classname]#MasterDetailEditor# (see below)
+|[literal]#++@ManyToMany++#|Selectable [classname]#Table#
+
+|===============
+
+
+
+The field factory is recusive, so that you can edit a complex object tree with
+one form.
+
+[[jpacontainer.fieldfactory.configuring]]
+== Configuring the Field Factory
+
+The [classname]#FieldFactory# is highly configurable with various configuration
+settings and by
+extending.////
+You need to make the configuration
+before
+////
+
+The [methodname]#setMultiSelectType()# and [methodname]#setSingleSelectType()#
+allow you to specify a selection component that is used instead of the default
+for a field with [literal]#++@ManyToMany++# and [literal]#++@ManyToOne++#
+annotation, respectively. The first parameter is the class type of the field,
+and the second parameter is the class type of a selection component. It must be
+a sub-class of [classname]#AbstractSelect#.
+
+The [methodname]#setVisibleProperties()# controls which properties (fields) are
+visible in generated forms, subforms, and tables. The first paramater is the
+class type for which the setting should be made, followed by the IDs of the
+visible properties.
+
+The configuration should be done before binding the form to a data source as
+that is when the field generation is done.
+
+Further configuration must be done by extending the many protected methods.
+Please see the API documentation for the complete list.
+
+
+[[jpacontainer.fieldfactory.using]]
+== Using the Field Factory
+
+The most basic use case for the JPAContainer [classname]#FieldFactory# is with a
+[classname]#Form# bound to a container item:
+
+
+----
+// Have a persistent container
+final JPAContainer<Country> countries =
+ JPAContainerFactory.make(Country.class, "book-examples");
+
+// For selecting an item to edit
+final ComboBox countrySelect =
+ new ComboBox("Select a Country", countries);
+countrySelect.setItemCaptionMode(Select.ITEM_CAPTION_MODE_PROPERTY);
+countrySelect.setItemCaptionPropertyId("name");
+
+// Country Editor
+final Form countryForm = new Form();
+countryForm.setCaption("Country Editor");
+countryForm.addStyleName("bordered"); // Custom style
+countryForm.setWidth("420px");
+countryForm.setBuffered(true);
+countryForm.setEnabled(false);
+
+// When an item is selected from the list...
+countrySelect.addValueChangeListener(new ValueChangeListener(){
+ @Override
+ public void valueChange(ValueChangeEvent event) {
+ // Get the item to edit in the form
+ Item countryItem =
+ countries.getItem(event.getProperty().getValue());
+
+ // Use a JPAContainer field factory
+ // - no configuration is needed here
+ final FieldFactory fieldFactory = new FieldFactory();
+ countryForm.setFormFieldFactory(fieldFactory);
+
+ // Edit the item in the form
+ countryForm.setItemDataSource(countryItem);
+ countryForm.setEnabled(true);
+
+ // Handle saves on the form
+ final Button save = new Button("Save");
+ countryForm.getFooter().removeAllComponents();
+ countryForm.getFooter().addComponent(save);
+ save.addClickListener(new ClickListener() {
+ @Override
+ public void buttonClick(ClickEvent event) {
+ try {
+ countryForm.commit();
+ countryForm.setEnabled(false);
+ } catch (InvalidValueException e) {
+ }
+ }
+ });
+ }
+});
+countrySelect.setImmediate(true);
+countrySelect.setNullSelectionAllowed(false);
+----
+See the http://demo.vaadin.com/book-examples-vaadin7/book#jpacontainer.fieldfactory.formonetoone[on-line example, window="_blank"].
+
+This would create a form shown in <<figure.jpacontainer.fieldfactory.using>>.
+
+[[figure.jpacontainer.fieldfactory.using]]
+.Using FieldFactory with One-to-Many Relationship
+image::img/fieldfactory-form.png[]
+
+If you use Hibernate, you also need to pass an
+[classname]#EntityManagerPerRequestHelper#, either for the constructor or with
+[methodname]#setEntityManagerPerRequestHelper()#
+ifdef::web[]
+, as described in
+<<dummy/../../../framework/jpacontainer/jpacontainer-hibernate#jpacontainer.hibernate.em-per-request,"The
+EntityManager-Per-Request
+pattern">>
+endif::web[]
+.
+
+
+[[jpacontainer.fieldfactory.masterdetaileditor]]
+== Master-Detail Editor
+
+The [classname]#MasterDetailEditor# is a field component that allows editing an
+item property that has one-to-many relationship. The item can be a row in a
+table or bound to a form. It displays the referenced collection as an editable
+[classname]#Table# and allows adding and removing items in it.
+
+You can use the [classname]#MasterDetailEditor# manually, or perhaps more
+commonly use a JPAContainer [classname]#FieldFactory# to create it
+automatically. As shown in the example in
+<<figure.jpacontainer.fieldfactory.using>>, the factory creates a
+[classname]#MasterDetailEditor# for all properties with a
+[literal]#++@OneToMany++# or an [literal]#++@ElementCollection++# annotation.
+
+
+
+