Statistics
| Revision:

gvsig-tools / org.gvsig.tools / library / trunk / org.gvsig.tools / org.gvsig.tools.dynform / org.gvsig.tools.dynform.services / src / main / java / org / gvsig / tools / dynform / services / dynform / AbeilleJDynForm.java @ 2547

History | View | Annotate | Download (20.9 KB)

1
package org.gvsig.tools.dynform.services.dynform;
2

    
3
import java.awt.Component;
4
import java.io.FileInputStream;
5
import java.io.InputStream;
6
import java.util.HashMap;
7
import java.util.Map;
8

    
9
import javax.swing.JCheckBox;
10
import javax.swing.JComboBox;
11
import javax.swing.JComponent;
12
import javax.swing.JSpinner;
13
import javax.swing.text.JTextComponent;
14

    
15
import org.gvsig.tools.dynform.DynFormDefinition;
16
import org.gvsig.tools.dynform.DynFormFieldDefinition;
17
import org.gvsig.tools.dynform.JDynFormField;
18
import org.gvsig.tools.dynform.JDynFormField.JDynFormFieldListener;
19
import org.gvsig.tools.dynform.spi.dynform.AbstractJDynForm;
20
import org.gvsig.tools.dynform.spi.DynFormSPIManager;
21

    
22
import com.jeta.forms.components.panel.FormPanel;
23
import java.awt.event.ActionEvent;
24
import java.awt.event.ActionListener;
25
import java.io.File;
26
import java.util.ArrayList;
27
import java.util.Iterator;
28
import java.util.List;
29
import javax.swing.JButton;
30
import javax.swing.JLabel;
31
import javax.swing.JList;
32
import javax.swing.JScrollPane;
33
import javax.swing.JTable;
34
import javax.swing.JTextArea;
35
import javax.swing.JViewport;
36
import org.apache.commons.io.FilenameUtils;
37
import org.apache.commons.io.IOUtils;
38
import org.apache.commons.lang3.StringUtils;
39
import org.gvsig.tools.dataTypes.CoercionException;
40
import org.gvsig.tools.dynform.spi.DynFormSPIManager.ComponentsFactory;
41
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.TAG_DYNFORM_ABEILLE_FORM;
42
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_CLEAR;
43
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ISMODIFIED;
44
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ISREADONLY;
45
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ONFIELDCHANGED;
46
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ONFIELDENTER;
47
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ONFIELDEXIT;
48
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ONLOAD;
49
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_ONSETVALUES;
50
import static org.gvsig.tools.dynform.spi.DynFormSPIManager.USERCODE_FORM_VALIDATE;
51
import org.gvsig.tools.dynform.spi.dynform.JDynFormFactory;
52
import org.gvsig.tools.dynform.spi.dynformfield.AbstractJDynFormField;
53
import org.gvsig.tools.dynform.spi.dynformfield.JDynFormFieldFactory;
54
import org.gvsig.tools.dynobject.DynObject;
55
import org.gvsig.tools.resourcesstorage.ResourcesStorage;
56
import org.gvsig.tools.resourcesstorage.ResourcesStorage.Resource;
57
import org.gvsig.tools.script.Script;
58

    
59
@SuppressWarnings("UseSpecificCatch")
60
public class AbeilleJDynForm extends AbstractJDynForm implements JDynFormFieldListener {
61

    
62
    private class AbeilleComponentsFactory implements ComponentsFactory {
63

    
64
        private class DefaultScrolledComponent<T> implements ScrolledComponent<T> {
65
            private final T component;
66
            
67
            public DefaultScrolledComponent(T component) {
68
                this.component = component;
69
            }
70

    
71
            @Override
72
            public JScrollPane getScrollPane() {
73
                try {
74
                    Object p1 = ((JComponent) component).getParent();
75
                    if( p1 instanceof JViewport ) {
76
                        p1 = ((JComponent) component).getParent();
77
                    }
78
                    if( p1 instanceof JScrollPane ) {
79
                        return (JScrollPane) p1;
80
                    }
81
                } catch(Exception ex) {
82

    
83
                }
84
                return null;
85
            }
86

    
87
            @Override
88
            public T getComponent() {
89
                return this.component;
90
            }
91
        }
92

    
93
        private static final String PREFIX_JCHECKBOX = "chk";
94
        private static final String PREFIX_JLABEL = "lbl";
95
        private static final String PREFIX_DROPDOWN = "lblDdn";
96
        private static final String PREFIX_JCOMBOBOX = "cbo";
97
        private static final String PREFIX_JSPINNER = "spn";
98
        private static final String PREFIX_JTEXTFIELD = "txt";
99
        private static final String PREFIX_JTEXTAREA = "txt";
100
        private static final String PREFIX_JBUTTON = "btn";
101
        private static final String PREFIX_JLIST = "lst";
102
        private static final String PREFIX_JTABLE = "tbl";
103
        
104
        private final FormPanel form;
105

    
106
        public AbeilleComponentsFactory(FormPanel form) {
107
            this.form = form;
108
        }
109
        
110
        @Override
111
        public boolean containsComponents(DynFormFieldDefinition definition) {
112
            String[] prefixes = new String[] {
113
                PREFIX_JCHECKBOX,
114
                PREFIX_JLABEL,
115
                PREFIX_DROPDOWN,
116
                PREFIX_JCOMBOBOX,
117
                PREFIX_JSPINNER,
118
                PREFIX_JTEXTFIELD,
119
                PREFIX_JTEXTAREA,
120
                PREFIX_JBUTTON,
121
                PREFIX_JLIST,
122
                PREFIX_JTABLE
123
            };
124
            for (String prefix : prefixes) {
125
                Component component = this.form.getComponentByName(prefix + definition.getName());
126
                if( component!=null ) {
127
                    return true;
128
                }
129
            }
130
            return false;
131
        }
132

    
133
        @Override
134
        public boolean containsJComboBox(DynFormFieldDefinition definition, String prefix) {
135
            Component component = this.form.getComponentByName(PREFIX_JCOMBOBOX+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
136
            return component!=null;
137
        }
138

    
139
        @Override
140
        public boolean containsJButton(DynFormFieldDefinition definition, String prefix) {
141
            Component component = this.form.getComponentByName(PREFIX_JBUTTON+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
142
            return component!=null;
143
        }
144

    
145
        @Override
146
        public boolean containsJLabel(DynFormFieldDefinition definition, String prefix) {
147
            Component component = this.form.getComponentByName(PREFIX_JLABEL+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
148
            return component!=null;
149
        }
150

    
151
        @Override
152
        public boolean containsJSpinner(DynFormFieldDefinition definition, String prefix) {
153
            Component component = this.form.getComponentByName(PREFIX_JSPINNER+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
154
            return component!=null;
155
        }
156

    
157
        @Override
158
        public boolean containsJTextField(DynFormFieldDefinition definition, String prefix) {
159
            Component component = this.form.getComponentByName(PREFIX_JTEXTFIELD+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
160
            return component!=null;
161
        }
162

    
163
        @Override
164
        public JCheckBox getJCheckBox(DynFormFieldDefinition definition, String prefix) {
165
            try {
166
                Component component = this.form.getComponentByName(PREFIX_JCHECKBOX+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
167
                return (JCheckBox) component;
168
            } catch(Throwable th) {
169
                return null;
170
            }
171
        }
172

    
173
        @Override
174
        public JLabel getJLabel(DynFormFieldDefinition definition, String prefix) {
175
            try {
176
                Component component = this.form.getComponentByName(PREFIX_JLABEL+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
177
                return (JLabel) component;
178
            } catch(Throwable th) {
179
                return null;
180
            }
181
        }
182

    
183
        @Override
184
        public JComboBox getJComboBox(DynFormFieldDefinition definition, String prefix) {
185
            try {
186
                Component component = this.form.getComponentByName(PREFIX_JCOMBOBOX+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
187
                return (JComboBox) component;
188
            } catch(Throwable th) {
189
                return null;
190
            }
191
        }
192

    
193
        @Override
194
        public JTextComponent getJTextField(DynFormFieldDefinition definition, String prefix) {
195
            try {
196
                Component component = this.form.getComponentByName(PREFIX_JTEXTFIELD+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
197
                return (JTextComponent) component;
198
            } catch(Throwable th) {
199
                return null;
200
            }
201
        }
202

    
203
        @Override
204
        public JTextComponent getJPasswordField(DynFormFieldDefinition definition, String prefix) {
205
            return this.getJTextField(definition, prefix);
206
        }
207

    
208
        @Override
209
        public ScrolledComponent<JTextArea> getJTextArea(DynFormFieldDefinition definition, String prefix) {
210
            try {
211
                JTextArea component = (JTextArea) this.form.getComponentByName(
212
                        PREFIX_JTEXTAREA + StringUtils.defaultIfBlank(prefix, "") + definition.getName()
213
                );
214
                return new DefaultScrolledComponent<>(component);
215
            } catch(Throwable th) {
216
                return null;
217
            }
218
        }
219

    
220
        @Override
221
        public ScrolledComponent<JList> getJList(DynFormFieldDefinition definition, String prefix) {
222
            try {
223
                JList component = (JList) this.form.getComponentByName(
224
                        PREFIX_JLIST+StringUtils.defaultIfBlank(prefix, "") + definition.getName()
225
                );
226
                return new DefaultScrolledComponent<>(component);
227
            } catch(Throwable th) {
228
                return null;
229
            }
230
        }
231

    
232
        @Override
233
        public ScrolledComponent<JTable> getJTable(DynFormFieldDefinition definition, String prefix) {
234
            try {
235
                JTable component = (JTable) this.form.getComponentByName(
236
                        PREFIX_JTABLE+StringUtils.defaultIfBlank(prefix, "") + definition.getName()
237
                );
238
                return new DefaultScrolledComponent<>(component);
239
            } catch(Throwable th) {
240
                return null;
241
            }
242
        }
243

    
244
        
245
        @Override
246
        public JSpinner getJSpinner(DynFormFieldDefinition definition, String prefix) {
247
            try {
248
                Component component = this.form.getComponentByName(PREFIX_JSPINNER+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
249
                return (JSpinner) component;
250
            } catch(Throwable th) {
251
                return null;
252
            }
253
        }
254
        
255
        @Override
256
        public JButton getJButton(DynFormFieldDefinition definition, String prefix) {
257
            try {
258
                Component component = this.form.getComponentByName(PREFIX_JBUTTON+StringUtils.defaultIfBlank(prefix, "") + definition.getName());
259
                return (JButton) component;
260
            } catch(Throwable th) {
261
                return null;
262
            }
263
        }
264
        
265
        
266
    }
267
    private Map<String,JDynFormField> components = null;
268
    private String resourceName = null;
269
    private AbeilleComponentsFactory componentsFactory;
270

    
271

    
272
    public AbeilleJDynForm(
273
            DynFormSPIManager manager,
274
            JDynFormFactory factory,
275
            DynFormContext context,
276
            DynFormDefinition definition
277
    ) {
278
        super(manager, factory, definition, context);
279
        this.components = new HashMap();
280
        resourceName = (String) definition.getTags().get(DynFormSPIManager.TAG_DYNFORM_ABEILLE_FORM);
281
        if (resourceName == null) {
282
            ResourcesStorage storage = context.getResourcesStorage();
283
            if( storage.exists("jetaform") ) {
284
                this.resourceName = "jetaform";
285
            } else if( storage.exists("jfrm") ) {
286
                this.resourceName = "jfrm";
287
            } else {
288
                throw new IllegalArgumentException("Can't locate form resource. Need tag '"+TAG_DYNFORM_ABEILLE_FORM+"' or resource 'jetaform'.");
289
            }
290
        }
291
        this.componentsFactory = null;
292
    }
293

    
294
    @Override
295
    public JComponent getFieldsContainer() {
296
        InputStream is = null;
297
        FormPanel form = null;
298
        Resource resource = null;
299
        try {
300
            File f = new File(resourceName);
301
            if( f.isAbsolute() && f.exists() ) {
302
                is = new FileInputStream(f);
303
            } else {
304
                ResourcesStorage storage = this.getContext().getResourcesStorage();
305
                resource = storage.getResource(FilenameUtils.getName(resourceName));
306
                if( resource == null || !resource.exists() ) {
307
                    throw new IllegalArgumentException("Can't locate abeille form '"+resourceName+"'.");
308
                }
309
                is = resource.asInputStream();
310
            }
311
            form = new FormPanel(is);
312
            this.componentsFactory = new AbeilleComponentsFactory(form);
313
            for (DynFormFieldDefinition definition : this.getDefinition().getDefinitions()) {
314
                if( definition==null ) {
315
                    continue;
316
                }
317
                if (definition.isHidden()) {
318
                    continue;
319
                }
320
                if( !this.componentsFactory.containsComponents(definition) ) {
321
                    continue;
322
                }
323
                try {
324
                    JDynFormFieldFactory factory = this.getServiceManager()
325
                            .getJDynFormFieldFactory(this.getContext(),definition);
326
                    JDynFormField jfield = factory.create(
327
                            this.getServiceManager(), 
328
                            this.componentsFactory, 
329
                            definition, 
330
                            null
331
                    );
332
                    if (jfield instanceof AbstractJDynFormField) {
333
                        ((AbstractJDynFormField) jfield).setForm(this);
334
                    }
335
                    if (this.isReadOnly()) {
336
                        jfield.setReadOnly(true);
337
                    } else {
338
                        jfield.setReadOnly(definition.isReadOnly());
339
                    }
340
                    jfield.addListener(this); 
341
                    
342
                    this.configurePopupMenu(jfield);
343
                    
344
                    this.components.put(jfield.getName(), jfield);
345
                    jfield.asJComponent(); // Forzamos que se inicialize
346
                    jfield.getJLabel();  // Forzamos que se inicialize 
347
                } catch(Throwable th1) {
348
                    LOGGER.warn("Can't load field '"+definition.getName()+"' for abeille form '"+resourceName+"'.", th1);
349
                }
350
            }
351
            this.bindUserCode(form);
352
            this.callUserEvent(USERCODE_FORM_ONLOAD, this);
353
        } catch (Throwable th) {
354
            LOGGER.warn("Can't load abeille form '"+resourceName+"'.", th);
355
        } finally {
356
            IOUtils.closeQuietly(is);
357
            IOUtils.closeQuietly(resource);
358
        }
359

    
360
        return form;
361
    }
362
    
363
    public Iterator getFieldsIterator() {
364
        if (!this.isContentsInitialized()) {
365
            this.initComponents();
366
        }
367
        return this.components.values().iterator();
368
    }
369

    
370
    @Override
371
    public void setReadOnly(boolean readOnly) {
372
        if( this.isReadOnly() == readOnly ) {
373
            return;
374
        }
375
        super.setReadOnly(readOnly);
376
        if (this.isContentsInitialized()) {
377
            Iterator it = this.getFieldsIterator();
378
            while (it.hasNext()) {
379
                JDynFormField field = (JDynFormField) it.next();
380
                if( readOnly ) {
381
                    field.setReadOnly(true);
382
                } else if( field.getDefinition().isReadOnly() ) {
383
                    field.setReadOnly(true);
384
                } else {
385
                    field.setReadOnly(false);
386
                }
387
            }
388
        }
389
    }
390

    
391
    private void bindUserCode(FormPanel form) {
392
        Script theScript = this.getScript();
393
        if( theScript==null ) {
394
            return;
395
        }        
396
        List<String> names = theScript.getNames();
397
        if( names == null ) {
398
            return;
399
        }
400
        for(String name : names ) {
401
            if( name.endsWith("_click") ) {
402
                String componentName = name.substring(0, name.length()-6);
403
                Component c = form.getComponentByName(componentName);
404
                if( c instanceof JButton ) {
405
                    JButton button = (JButton) c;
406
                    final String fnName = name;
407
                    button.addActionListener(new ActionListener() {
408
                        @Override
409
                        public void actionPerformed(ActionEvent e) {
410
                            callUserEvent(fnName, e);
411
                        }
412
                    });
413
                }
414
            }
415
        }
416
    }
417

    
418
    @Override
419
    public void setValues(DynObject values) {
420
        if (!this.isContentsInitialized()) {
421
            this.values = values;
422
            return;
423
        }
424
        for (JDynFormField jfield : this.getFields()) {
425
            String name = "unknown";
426
            try {
427
                name = jfield.getName();
428
                jfield.setValue(values.getDynValue(jfield.getName()));
429
            } catch(Exception ex) {
430
                LOGGER.warn("Can't set value to field '"+name+"'.",ex);
431
            }
432
        }
433
        this.callUserEvent(USERCODE_FORM_ONSETVALUES, this, values);
434
        try {
435
            if( (boolean) this.callUserFunction(USERCODE_FORM_ISREADONLY, this) ) {
436
                this.setReadOnly(true);
437
            }
438
        } catch (Exception ex) {
439
        }
440
        
441
    }
442

    
443
    public Iterable<JDynFormField> getFields() {
444
        if (!this.isContentsInitialized()) {
445
            this.initComponents();
446
        }
447
        return this.components.values();
448
    }
449

    
450
    @Override
451
    public JDynFormField getField(String fieldName) {
452
        if (!this.isContentsInitialized()) {
453
            this.initComponents();
454
        }
455
        JDynFormField field = this.components.get(fieldName);
456
        return field;
457
    }
458

    
459
    @Override
460
    public void getValues(DynObject values) {
461
        if (values == null) {
462
            return;
463
        }
464
        for (JDynFormField jfield : this.getFields()) {
465
            try {
466
                jfield.fetch(values);
467
            } catch (Exception ex) {
468
                LOGGER.warn("Can't get value of field '" + jfield.getName() + "'.", ex);
469
            }
470
        }
471
    }
472

    
473
    @Override
474
    public Object getValue(String fieldName) {
475
        JDynFormField field = (JDynFormField) this.getField(fieldName);
476
        return field.getValue();
477
    }
478

    
479
    @Override
480
    public void setValue(String fieldName, Object value) {
481
        JDynFormField field = (JDynFormField) this.getField(fieldName);
482
        try {
483
            value = field.getDefinition().getDataType().coerce(value);
484
        } catch (CoercionException e) {
485
            String msg = "Invalid value '" + ((value == null) ? "(null)" : value.toString()) + "' for field '" + fieldName + "'.";
486
            LOGGER.warn(msg, e);
487
            throw new RuntimeException(msg, e);
488
        }
489
        field.setValue(value);
490
    }
491

    
492
    @Override
493
    public boolean hasValidValues() {
494
        for (JDynFormField jfield : this.getFields()) {
495
            if (!jfield.hasValidValue()) {
496
                return false;
497
            }
498
        }
499
        try {
500
            return (boolean) this.callUserFunction(USERCODE_FORM_VALIDATE, this);
501
        } catch (Exception ex) {
502
        }
503
        return true;
504
    }
505

    
506
    @Override
507
    public boolean hasValidValues(List<String> fieldsName) {
508
        if (fieldsName == null) {
509
            fieldsName = new ArrayList<>();
510
        }
511
        for (JDynFormField jfield : this.getFields()) {
512
            if (!jfield.hasValidValue()) {
513
                fieldsName.add(jfield.getName());
514
            }
515
        }
516
        return fieldsName.isEmpty();
517
    }
518

    
519
    @Override
520
    public boolean isModified() {
521
        if( this.isReadOnly() ) {
522
            return false;
523
        }
524
        try {
525
            if( this.getScript()!=null ) {
526
                return (boolean) this.callUserFunction(USERCODE_FORM_ISMODIFIED, this, values);
527
            }
528
        } catch (NoSuchMethodException ex) {
529
        } catch (Exception ex) {
530
            LOGGER.warn("Error calling user function form_IsModified.",ex);
531
        }
532
        for (JDynFormField jfield : this.getFields()) {
533
            if (jfield.isModified()) {
534
                return true;
535
            }
536
        }
537
        return false;
538
    }
539

    
540
    @Override
541
    public void clear() {
542
        for (JDynFormField jfield : this.getFields()) {
543
            jfield.clear();
544
        }
545
        this.callUserEvent(USERCODE_FORM_CLEAR, this);
546
    }
547

    
548
    @Override
549
    public void fieldEnter(JDynFormField field) {
550
        message(field.getDefinition().getDescription());
551
        this.callUserEvent(USERCODE_FORM_ONFIELDENTER, this, field);
552
    }
553

    
554
    @Override
555
    public void fieldExit(JDynFormField field) {
556
        message();
557
        this.callUserEvent(USERCODE_FORM_ONFIELDEXIT, this, field);
558
    }
559

    
560
    @Override
561
    public void fieldChanged(JDynFormField field) {
562
        fireFieldChangeEvent(field);
563
        this.callUserEvent(USERCODE_FORM_ONFIELDCHANGED, this, field);
564
    }
565

    
566
    @Override
567
    public void message(JDynFormField field, String message) {
568
        message(message);
569
    }
570

    
571
}