Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.compat.cdc / org.gvsig.fmap.dal / org.gvsig.fmap.dal.swing / org.gvsig.fmap.dal.swing.impl / src / main / java / org / gvsig / fmap / dal / swing / impl / featuretype / DefaultFeatureTypePanel.java @ 45739

History | View | Annotate | Download (26.1 KB)

1
package org.gvsig.fmap.dal.swing.impl.featuretype;
2

    
3
import org.gvsig.fmap.dal.swing.featuretype.FeatureTypePanel;
4
import java.awt.BorderLayout;
5
import java.awt.Dimension;
6
import java.awt.event.ActionEvent;
7
import java.awt.event.ActionListener;
8
import java.util.ArrayList;
9
import java.util.Objects;
10
import javax.swing.AbstractAction;
11
import javax.swing.JComponent;
12
import javax.swing.JOptionPane;
13
import javax.swing.JPanel;
14
import javax.swing.JScrollBar;
15
import javax.swing.JScrollPane;
16
import javax.swing.JSplitPane;
17
import javax.swing.event.ChangeListener;
18
import javax.swing.event.ListSelectionEvent;
19
import javax.swing.event.ListSelectionListener;
20
import javax.swing.event.TableModelEvent;
21
import javax.swing.table.AbstractTableModel;
22
import org.apache.commons.lang3.StringUtils;
23
import org.gvsig.configurableactions.ConfigurableActionsMamager;
24
import org.gvsig.expressionevaluator.ExpressionUtils;
25
import org.gvsig.fmap.dal.feature.EditableFeatureAttributeDescriptor;
26
import org.gvsig.fmap.dal.feature.EditableFeatureType;
27
import org.gvsig.fmap.dal.feature.FeatureAttributeDescriptor;
28
import org.gvsig.fmap.dal.feature.FeatureRule;
29
import org.gvsig.fmap.dal.feature.FeatureStore;
30
import org.gvsig.fmap.dal.feature.FeatureType;
31
import org.gvsig.texteditor.JTextEditor;
32
import org.gvsig.tools.ToolsLocator;
33
import org.gvsig.tools.dataTypes.DataType;
34
import org.gvsig.tools.dataTypes.DataTypes;
35
import org.gvsig.tools.dynobject.DynStruct_v2;
36
import org.gvsig.tools.i18n.I18nManager;
37
import org.gvsig.tools.swing.api.ChangeListenerHelper;
38
import org.gvsig.tools.swing.api.ToolsSwingLocator;
39
import org.gvsig.tools.swing.api.ToolsSwingManager;
40
import org.gvsig.tools.swing.api.threadsafedialogs.ThreadSafeDialogsManager;
41
import org.gvsig.tools.swing.api.windowmanager.WindowManager;
42
import org.gvsig.tools.util.ToolsUtilLocator;
43
import org.slf4j.Logger;
44
import org.slf4j.LoggerFactory;
45

    
46
/**
47
 *
48
 * @author jjdelcerro
49
 */
50
public class DefaultFeatureTypePanel 
51
        extends DefaultFeatureTypePanelView
52
        implements FeatureTypePanel
53
    {
54

    
55
    private static final Logger LOGGER = LoggerFactory.getLogger(DefaultFeatureTypePanel.class);
56

    
57
    private FeatureType originalFeatureType = null;
58
    private JSplitPane splRules;
59
    private JSplitPane splAttributes;
60

    
61
    private class FeatureTypeTableModel extends AbstractTableModel {
62

    
63
        private final FeatureType featureType;
64
        private final String[] columnNames = new String[] {
65
          "Name",
66
          "Type",
67
          "Size",
68
          "Precision",
69
          "Scale",
70
          "Default value",
71
          "Calculated",
72
          "Fk"
73
        };
74
        private final Class[] columnClasses = new Class[] {
75
          String.class,
76
          String.class,
77
          Integer.class,
78
          Integer.class,
79
          Integer.class,
80
          String.class,
81
          Boolean.class,
82
          Boolean.class
83
        };
84
        
85
        public FeatureTypeTableModel() {
86
            this.featureType = null;
87
        }
88
        
89
        public FeatureTypeTableModel(FeatureType featureType) {
90
            this.featureType = featureType;
91
        }
92
        
93
        @Override
94
        public int getRowCount() {
95
            if( this.featureType==null ) {
96
                return 0;
97
            }
98
            return this.featureType.size();
99
        }
100

    
101
        @Override
102
        public int getColumnCount() {
103
            if( this.featureType==null ) {
104
                return 0;
105
            }
106
            return this.columnNames.length;
107
        }
108

    
109
        @Override
110
        public String getColumnName(int columnIndex) {
111
            if( this.featureType==null ) {
112
                return "";
113
            }
114
            return this.columnNames[columnIndex];
115
        }
116

    
117
        @Override
118
        public Class<?> getColumnClass(int columnIndex) {
119
            if( this.featureType==null ) {
120
                return String.class;
121
            }
122
            return this.columnClasses[columnIndex];
123
        }
124

    
125
        @Override
126
        public boolean isCellEditable(int rowIndex, int columnIndex) {
127
            return false;
128
        }
129

    
130
        @Override
131
        public Object getValueAt(int rowIndex, int columnIndex) {
132
            if( this.featureType==null ) {
133
                return "";
134
            }
135
            FeatureAttributeDescriptor descriptor = this.featureType.getAttributeDescriptor(rowIndex);
136
            DataType dataType = descriptor.getDataType();
137
            switch(columnIndex) {
138
                case 0:
139
                    return descriptor.getName();
140
                case 1:
141
                    return descriptor.getDataTypeName();
142
                case 2:
143
                    if( dataType.supportSize() ) {
144
                      return descriptor.getSize();
145
                    }
146
                    return null;
147
                case 3:
148
                    if( dataType.supportPrecision()) {
149
                      return descriptor.getPrecision();
150
                    }
151
                    return null;
152
                case 4:
153
                    if( dataType.supportScale()) {
154
                      return descriptor.getScale();
155
                    }
156
                    if( dataType.isNumeric() ) {
157
                      return 0;
158
                    }
159
                    return null;
160
                case 5:
161
                    return Objects.toString(descriptor.getDefaultValue(),"");
162
                case 6:
163
                    return descriptor.isComputed();
164
                case 7:
165
                    return descriptor.isForeingKey();
166
                default:
167
                    return "";
168
            }
169
        }
170

    
171
        @Override
172
        public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
173
        }
174
    
175
        public void fireUpdateEvent() {
176
            this.fireTableChanged(new TableModelEvent(this));
177
        }
178
    }
179
    
180
    public static class ViewAsJsonAction extends AbstractAction {
181
        
182
        @SuppressWarnings("OverridableMethodCallInConstructor")
183
        public ViewAsJsonAction() {
184
            I18nManager i18n = ToolsLocator.getI18nManager();
185

    
186
            this.putValue(NAME, i18n.getTranslation("_View_as_Json"));
187
            this.putValue(ACTION_COMMAND_KEY, "ViewAsJson");
188
        }
189

    
190
        @Override
191
        public Object getValue(String key) {
192
            if (NAME.equals(key)) {
193
                // Cuando se registra la accion aun no se han cargado las traducciones
194
                I18nManager i18n = ToolsLocator.getI18nManager();
195
                return i18n.getTranslation("_View_as_Json");
196
            }
197
            return super.getValue(key);
198
        }
199
        @Override
200
        public void actionPerformed(ActionEvent e) {
201
            DefaultFeatureTypePanel featureTypePanel = (DefaultFeatureTypePanel) e.getSource();
202
            FeatureType featureType = featureTypePanel.fetch(null);
203

    
204
            JTextEditor editor = ToolsUtilLocator.getTextEditorManager().createTextEditor();
205
            editor.setText(featureType.toJsonBuilder().toString());
206

    
207
            WindowManager winmanager = ToolsSwingLocator.getWindowManager();
208
            winmanager.showWindow(
209
                    editor.asJComponent(), 
210
                    "FeatureType - "+featureType.getName(), 
211
                    WindowManager.MODE.WINDOW
212
            );
213
        }
214
        
215
    }
216
    
217
    private DefaultFeatureAttributePanel descriptorPanel;
218
    private EditableFeatureType featureType;
219
    private int mode;
220
    private FeatureTypeTableModel tableModel;
221
    private FeatureStore store;
222
    private int currentRow;
223
    private boolean fieldSelectionAllowed;
224
    private TagsController tagsController;
225
    private ChangeListenerHelper changeListenerHelper;
226
    private AggregateController<FeatureRule> rulesController;
227
        
228
    public DefaultFeatureTypePanel() {
229
        this.mode = MODE_SHOW_ONLY;
230
        this.currentRow = -1;
231
        this.fieldSelectionAllowed = true;
232
        this.initComponents();
233
    }
234
    
235
    private JSplitPane createVerticalSplit(JPanel container, JPanel top, boolean scrolltop, JPanel bottom, boolean scrollbottom) {
236
        JComponent compTop = top;
237
        JComponent compBottom = bottom;
238
        if( scrolltop ) {
239
                compTop = new JScrollPane(
240
                        top, 
241
                        JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,
242
                        JScrollPane.HORIZONTAL_SCROLLBAR_NEVER 
243
                );
244
        }
245
        if( scrollbottom ) {
246
                compBottom = new JScrollPane(
247
                        bottom, 
248
                        JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,
249
                        JScrollPane.HORIZONTAL_SCROLLBAR_NEVER 
250
                );
251
        }
252
        JSplitPane split = new JSplitPane(
253
                JSplitPane.VERTICAL_SPLIT,
254
                false,
255
                compTop,
256
                compBottom
257
        );
258
        split.setOneTouchExpandable(true);
259
        container.removeAll();
260
        container.setLayout(new BorderLayout());
261
        container.add(split, BorderLayout.CENTER);
262
        return split;
263
    }
264
    
265
    @SuppressWarnings("Convert2Lambda")
266
    private void initComponents() {
267
        ToolsSwingManager swingManager = ToolsSwingLocator.getToolsSwingManager();
268
        ConfigurableActionsMamager cfgActionsManager = ToolsUtilLocator.getConfigurableActionsMamager();
269
        JComponent c = cfgActionsManager.getConfigurableActionsComponent(CONFIGURABLE_PANEL_ID, this);
270
        this.pnlCfgActions.setLayout(new BorderLayout(0,0));
271
        this.pnlCfgActions.add(c, BorderLayout.CENTER);
272

    
273
        this.splRules = createVerticalSplit(
274
                this.gridRules, 
275
                this.gridRulesTable, false,
276
                this.gridRulesDetail, true
277
        );
278
        this.splAttributes = createVerticalSplit(
279
                this.gridAttributes,
280
                this.gridAttributesTable, false,
281
                this.gridAttributesDetail, true
282
        );
283
        
284
        this.changeListenerHelper = swingManager.createChangeListenerHelper();
285
        
286
        swingManager.translate(this.btnDelete);
287
        swingManager.translate(this.btnFormFieldAccept);
288
        swingManager.translate(this.btnFormFieldDiscard);
289
        swingManager.translate(this.btnFormFieldModify);
290
        swingManager.translate(this.btnNew);
291
        swingManager.translate(this.lblLabel);
292
        swingManager.translate(this.lblDescription);
293
        swingManager.translate(this.lblTags);
294
        swingManager.translate(this.tabFeatureType);
295
        swingManager.translate(this.lblRulesDefaultRules);
296
        swingManager.translate(this.lblRulesCustomRules);
297
        swingManager.translate(this.chkRulesValidateFeatureBeforeInsert);
298
        swingManager.translate(this.chkRulesValidateFeaturesAtFinishEditing);
299
        swingManager.translate(this.lblRuleName);
300
        swingManager.translate(this.lblRuleDescription);
301
        swingManager.translate(this.lblRuleCheckAtFinishEditing);
302
        swingManager.translate(this.lblRuleCheckAtUpdate);
303
        swingManager.translate(this.lblRuleValidation);
304
        swingManager.translate(this.btnRulesNew);
305
        swingManager.translate(this.btnRulesDelete);
306
        swingManager.translate(this.btnRuleFormFieldModify);
307
        swingManager.translate(this.btnRuleFormFieldAccept);
308
        swingManager.translate(this.btnRuleFormFieldDiscard);
309
        swingManager.translate(this.btnRuleValidation);
310
        swingManager.translate(this.btnRuleValidationBookmarks);
311
        swingManager.translate(this.btnRuleValidationHistory);
312
                
313
        this.tableModel = new FeatureTypeTableModel();
314
        this.tblFields.setModel(this.tableModel);
315
        this.tblFields.getSelectionModel().addListSelectionListener(new ListSelectionListener() {
316
            @Override
317
            public void valueChanged(ListSelectionEvent e) {
318
                if( e.getValueIsAdjusting() ) {
319
                    return;
320
                }
321
                doChangeFieldSelection();
322
            }
323
        });
324
        this.descriptorPanel = new DefaultFeatureAttributePanel();
325
        this.pnlField.setLayout(new BorderLayout());
326
        this.pnlField.add(this.descriptorPanel, BorderLayout.CENTER);
327
        this.descriptorPanel.setEnabled(false);
328

    
329
        this.btnFormFieldModify.addActionListener(new ActionListener() {
330
            @Override
331
            public void actionPerformed(ActionEvent e) {
332
                doFormFieldModify();
333
            }
334
        });
335
        this.btnFormFieldDiscard.addActionListener(new ActionListener() {
336
            @Override
337
            public void actionPerformed(ActionEvent e) {
338
                doFormFieldDiscard();
339
            }
340
        });
341
        this.btnFormFieldAccept.addActionListener(new ActionListener() {
342
            @Override
343
            public void actionPerformed(ActionEvent e) {
344
                doFormFieldAccept();
345
            }
346
        });
347
        this.btnNew.addActionListener(new ActionListener() {
348
            @Override
349
            public void actionPerformed(ActionEvent e) {
350
                doNewField();
351
            }
352
        });
353
        this.btnDelete.addActionListener(new ActionListener() {
354
            @Override
355
            public void actionPerformed(ActionEvent e) {
356
                doDeleteField();
357
            }
358
        });
359
        
360
        this.tagsController = new TagsController(
361
                tblTags, 
362
                cboTagsName, 
363
                cboTagsValue, 
364
                btnTagsAdd, 
365
                btnTagsUpdate, 
366
                btnTagsRemove,
367
                lblTagsDescription
368
        );
369

    
370
        FeatureRuleController ruleController = new FeatureRuleController(
371
                txtRuleName,
372
                txtRuleDescription,
373
                chkRuleCheckAtFinishEditing,
374
                chkRuleCheckAtUpdate,
375
                txtRuleValidation,
376
                btnRuleValidation,
377
                btnRuleValidationBookmarks, 
378
                btnRuleValidationHistory
379
        );
380
                
381
        this.rulesController = new DefaultAggregateController<>(
382
                this.tblRules, 
383
                this.btnRuleFormFieldModify, 
384
                this.btnRuleFormFieldDiscard, 
385
                this.btnRuleFormFieldAccept, 
386
                this.btnRulesNew, 
387
                this.btnRulesDelete,
388
                ruleController
389
        );
390

    
391
        this.setPreferredSize(new Dimension(700, 500));
392
        if( this.tblFields.getRowCount()>0 ) {
393
            this.tblFields.getSelectionModel().setSelectionInterval(0, 0);
394
            doFormFieldPut();
395
        }
396
    }
397
       
398
    private boolean doFormFieldFetch() {
399
        int row = this.tblFields.getSelectedRow();
400
        if (row < 0) {
401
            return true;
402
        }
403
        FeatureAttributeDescriptor descriptor = this.featureType.getAttributeDescriptor(row);
404
        int previousType = descriptor.getType();
405
        if (descriptor instanceof EditableFeatureAttributeDescriptor) {
406
            if (this.descriptorPanel.fetch((EditableFeatureAttributeDescriptor) descriptor) == null) {
407
                return false;
408
            }
409
            this.tableModel.fireUpdateEvent();
410
        }
411
        FeatureAttributeDescriptor oldDescriptor = null;
412
        if (this.originalFeatureType != null) {
413
            oldDescriptor = this.originalFeatureType.getAttributeDescriptor(descriptor.getName());
414
        }
415
        if (oldDescriptor != null
416
                && oldDescriptor.getDataType() != descriptor.getDataType()
417
                && previousType != descriptor.getType()) {
418
            ThreadSafeDialogsManager dialogs = ToolsSwingLocator.getThreadSafeDialogsManager();
419
            I18nManager i18manager = ToolsLocator.getI18nManager();
420
            StringBuilder message = new StringBuilder();
421

    
422
            String[] messageArgs = new String[]{oldDescriptor.getName()};
423
            message.append(i18manager.getTranslation("_Already_existed_a_field_named_XfieldnameX_but_with_different_data_type", messageArgs));
424
            message.append(".\n");
425
            message.append(i18manager.getTranslation("_Values_of_data_will_try_to_coerce_to_this_type"));
426
            dialogs.messageDialog(
427
                    message.toString(),
428
                    null,
429
                    i18manager.getTranslation("_Values_will_change"),
430
                    JOptionPane.INFORMATION_MESSAGE,
431
                    "feature-type-manager-field-already-exist-in-previous-schema");
432
        }
433

    
434
        return true;
435
    }
436
    
437
    private void doFormFieldPut() {
438
        int row = this.tblFields.getSelectedRow();
439
        if( row<0 ) {
440
            return;
441
        }
442
        FeatureAttributeDescriptor descriptor = this.featureType.getAttributeDescriptor(row);
443
        this.currentRow = row;
444
        this.descriptorPanel.put(descriptor);
445
        updateButtonState();
446
        if( descriptor instanceof EditableFeatureAttributeDescriptor ) {
447
            this.btnFormFieldModify.setEnabled((this.mode==MODE_EDIT_ALL || this.mode==MODE_EDIT_ONLY_METADATA) && this.tblFields.getSelectedRowCount()==1);
448
        } else {
449
            this.btnFormFieldModify.setEnabled(false);
450
        }
451
    }
452
    
453
    private void updateButtonState() {
454
        this.descriptorPanel.setEnabled(true);
455
        this.descriptorPanel.setMode(MODE_SHOW_ONLY);
456
        this.btnFormFieldAccept.setEnabled(false);
457
        this.btnFormFieldDiscard.setEnabled(false);
458
        
459
        switch(this.mode) {
460
            case MODE_EDIT_ALL:
461
                this.btnDelete.setEnabled(true);
462
                this.btnFormFieldModify.setEnabled(true);
463
                this.btnNew.setEnabled(true);
464
                this.tagsController.setEditable(true);
465
                this.txtLabel.setEditable(true);
466
                this.txtDescription.setEditable(true);
467
                break;
468
            case MODE_EDIT_ONLY_METADATA:
469
                this.btnDelete.setEnabled(this.descriptorPanel.isVirtualField());
470
                this.btnFormFieldModify.setEnabled(true);
471
                this.btnNew.setEnabled(true);
472
                this.tagsController.setEditable(true);
473
                this.txtLabel.setEditable(true);
474
                this.txtDescription.setEditable(true);
475
                break;
476
            case MODE_SHOW_ONLY:
477
                this.btnDelete.setEnabled(false);
478
                this.btnFormFieldModify.setEnabled(false);
479
                this.btnNew.setEnabled(false);
480
                this.tagsController.setEditable(false);
481
                this.txtLabel.setEditable(false);
482
                this.txtDescription.setEditable(false);
483
                break;
484
        }
485
    }
486
    
487
    private void doFormFieldModify() {
488
        int row = this.tblFields.getSelectedRow();
489
        if( row<0 ) {
490
            return;
491
        }
492
        FeatureAttributeDescriptor descriptor = this.featureType.getAttributeDescriptor(row);
493
        this.descriptorPanel.put(descriptor);
494
        this.descriptorPanel.setEnabled(this.mode==MODE_EDIT_ALL || this.mode==MODE_EDIT_ONLY_METADATA);
495
        this.btnFormFieldAccept.setEnabled(this.mode==MODE_EDIT_ALL || this.mode==MODE_EDIT_ONLY_METADATA);
496
        this.btnFormFieldDiscard.setEnabled(this.mode==MODE_EDIT_ALL || this.mode==MODE_EDIT_ONLY_METADATA);
497
        this.btnFormFieldModify.setEnabled(false);
498
        this.btnNew.setEnabled(false);
499
        this.btnDelete.setEnabled(false);
500
        if( descriptor instanceof EditableFeatureAttributeDescriptor ) {
501
            this.descriptorPanel.setMode(this.mode);
502
        } else {
503
            this.descriptorPanel.setMode(MODE_SHOW_ONLY);
504
        }
505
        this.fieldSelectionAllowed = false;
506
        this.changeListenerHelper.fireEvent();
507
    }
508
    
509
    @Override
510
    public boolean isEditing() {
511
        return btnFormFieldAccept.isEnabled() || this.rulesController.isEditing();
512
    }
513
    
514
    private void doFormFieldAccept() {
515
        int row = this.tblFields.getSelectedRow();
516
        if( row<0 ) {
517
            return;
518
        }
519
        if( doFormFieldFetch() ) {
520
            this.updateButtonState();
521
            this.tblFields.getSelectionModel().setSelectionInterval(row, row);
522
            this.tblFields.scrollRectToVisible(this.tblFields.getCellRect(row, 0, true));
523
            this.fieldSelectionAllowed = true;
524
        }
525
        this.changeListenerHelper.fireEvent();
526
    }
527
    
528
    private void doFormFieldDiscard() {
529
        doFormFieldPut();
530
        this.updateButtonState();
531
        this.fieldSelectionAllowed = true;
532
        this.changeListenerHelper.fireEvent();
533
    }
534

    
535
    private void doChangeFieldSelection() {
536
        int row = this.tblFields.getSelectedRow();
537
        if( row<0 ) {
538
            return;
539
        }
540
        if( !this.fieldSelectionAllowed ) {
541
            if( row !=this.currentRow ) {
542
                I18nManager i18n = ToolsLocator.getI18nManager();
543
                JOptionPane.showMessageDialog(
544
                    this, 
545
                    i18n.getTranslation("_Before_changing_field_accept_or_discard_the_changes"), 
546
                    i18n.getTranslation("_Warning"), 
547
                    JOptionPane.WARNING_MESSAGE
548
                );
549
                this.tblFields.getSelectionModel().setSelectionInterval(
550
                        this.currentRow, 
551
                        this.currentRow
552
                );
553
            }
554
            return;
555
        }
556
        doFormFieldPut();   
557
    }
558
    
559
    @Override
560
    public JComponent asJComponent() {
561
        return this;
562
    }
563

    
564
    @Override
565
    public int getMode() {
566
        return this.mode;
567
    }
568
    
569
    @Override
570
    public void setMode(int mode) {
571
        this.mode = mode;
572
        updateButtonState();
573
    }
574

    
575
    @Override
576
    public EditableFeatureType fetch(EditableFeatureType type) {
577
        if( type == null ) {
578
            type = (EditableFeatureType) this.featureType.getCopy();
579
        } else {
580
            type.removeAll();
581
            type.copyFrom(this.featureType);
582
        }
583
        type.setLabel(
584
            StringUtils.defaultIfBlank(this.txtLabel.getText(), null)
585
        );
586
        type.setDescription(
587
            StringUtils.defaultIfBlank(this.txtDescription.getText(), null)
588
        );
589
        this.tagsController.fetch(type.getTags());
590
        return type;
591
    }
592

    
593
    @Override
594
    public void put(FeatureType type) {
595
        this.featureType = null;
596
        this.originalFeatureType = null;
597
        if (type == null) {
598
            this.store = null;
599
            this.rulesController.setModel(new FeatureRulesModel());
600
            this.chkRuleCheckAtFinishEditing.setSelected(false);
601
            this.chkRuleCheckAtUpdate.setSelected(true);
602
        } else {
603
            FeatureType ftypeToCompare = type.getOriginalFeatureType();
604
            if (ftypeToCompare == null) {
605
                ftypeToCompare = type;
606
            }
607
            this.originalFeatureType = ftypeToCompare.getCopy();
608
            this.featureType = (EditableFeatureType) type.getCopy();
609
            this.rulesController.setModel(new FeatureRulesModel(this.featureType.getRules()));
610
            this.chkRuleCheckAtFinishEditing.setSelected(type.isCheckFeaturesAtFinishEditing());
611
            this.chkRuleCheckAtUpdate.setSelected(type.isCheckFeaturesAtInsert());
612
            // Nos quedamos una referencia para evitar que se destruya, ya que
613
            // el featureType se guarda solo una WeakReference.
614
            this.store = type.getStore();
615
            this.txtLabel.setText(
616
                    StringUtils.defaultIfBlank(((DynStruct_v2) type).getLabel(), "")
617
            );
618
            this.txtDescription.setText(
619
                    StringUtils.defaultIfBlank(((DynStruct_v2) type).getDescription(), "")
620
            );
621
            this.tagsController.set(((DynStruct_v2) type).getTags());
622
        }
623
        if( !(type instanceof EditableFeatureType) ) {
624
            this.setMode(MODE_SHOW_ONLY);
625
        }
626
        this.tableModel = new FeatureTypeTableModel(this.featureType);
627
        this.tblFields.setModel(this.tableModel);
628
        if( type!=null && !type.isEmpty() ) {
629
            this.tblFields.getSelectionModel().setSelectionInterval(0, 0);
630
        }
631
        updateButtonState();
632
        doFormFieldPut();       
633
    }
634

    
635
    private void doNewField() {
636
        EditableFeatureType eft = (EditableFeatureType)this.featureType;
637
        EditableFeatureAttributeDescriptor descriptor = eft.add(
638
                this.featureType.getNewFieldName(), 
639
                DataTypes.STRING,
640
                50
641
        );
642
        if( this.mode == MODE_EDIT_ONLY_METADATA ) {
643
            descriptor.setFeatureAttributeEmulator(ExpressionUtils.createExpression("NULL"));
644
        }
645
        this.tableModel.fireUpdateEvent();
646
        int row = descriptor.getIndex();
647
        this.tblFields.getSelectionModel().addSelectionInterval(row,row);
648
        this.tblFields.scrollRectToVisible(this.tblFields.getCellRect(row, 0, true));
649
        updateButtonState();
650
        doFormFieldModify();    
651
        this.changeListenerHelper.fireEvent();
652
    }
653
    
654
    private void doDeleteField() {
655
        int row = this.tblFields.getSelectedRow();
656
        int[] rows = this.tblFields.getSelectedRows();
657
        ArrayList FeatureAttributeDescriptor;
658
        ArrayList<String> descriptors = new ArrayList<>();
659
        for (int rowDescriptor : rows) {
660
            if (rowDescriptor < 0) {
661
                continue;
662
            }
663
            descriptors.add(this.featureType.getAttributeDescriptor(rowDescriptor).getName());
664
        }
665
        for (String descriptor : descriptors) {
666
            ((EditableFeatureType)this.featureType).remove(descriptor);
667
        }
668
        this.tableModel.fireUpdateEvent();
669
        if( row >= this.tblFields.getRowCount()) {
670
            row = this.tblFields.getRowCount()-1;
671
        }
672
        this.tblFields.getSelectionModel().addSelectionInterval(row,row);
673
        updateButtonState();
674
        doFormFieldPut();       
675
        this.changeListenerHelper.fireEvent();
676
    }
677

    
678
    @Override
679
    public void addChangeListener(ChangeListener listener) {
680
        this.changeListenerHelper.addChangeListener(listener);
681
    }
682

    
683
    @Override
684
    public ChangeListener[] getChangeListeners() {
685
        return this.changeListenerHelper.getChangeListeners();
686
    }
687

    
688
    @Override
689
    public void removeChangeListener(ChangeListener listener) {
690
        this.changeListenerHelper.removeChangeListener(listener);
691
    }
692

    
693
    @Override
694
    public void removeAllChangeListener() {
695
        this.changeListenerHelper.removeAllChangeListener();
696
    }
697

    
698
    @Override
699
    public boolean hasChangeListeners() {
700
        return this.changeListenerHelper.hasChangeListeners();
701
    }
702
    
703
  public static void selfRegister() {
704
        ConfigurableActionsMamager cfgActionsManager = ToolsUtilLocator.getConfigurableActionsMamager();
705
        cfgActionsManager.addConfigurableAction(CONFIGURABLE_PANEL_ID, new ViewAsJsonAction());
706
  }
707
}