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 / featurequery / DefaultFeatureQueryCalculatedColumnsPanel.java @ 46251

History | View | Annotate | Download (33.2 KB)

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

    
3
import java.awt.Dimension;
4
import java.awt.event.ActionEvent;
5
import java.awt.event.ActionListener;
6
import java.net.URL;
7
import java.util.List;
8
import java.util.logging.Level;
9
import javax.swing.DefaultListModel;
10
import javax.swing.DefaultListSelectionModel;
11
import javax.swing.ImageIcon;
12
import javax.swing.JButton;
13
import javax.swing.JComboBox;
14
import javax.swing.JComponent;
15
import javax.swing.JList;
16
import javax.swing.JOptionPane;
17
import javax.swing.ListModel;
18
import javax.swing.ListSelectionModel;
19
import javax.swing.event.ChangeEvent;
20
import javax.swing.event.ChangeListener;
21
import javax.swing.event.DocumentEvent;
22
import javax.swing.event.DocumentListener;
23
import javax.swing.event.ListSelectionEvent;
24
import javax.swing.text.JTextComponent;
25
import org.apache.commons.io.FilenameUtils;
26
import org.apache.commons.lang.StringUtils;
27
import org.gvsig.configurableactions.ConfigurableActionsMamager;
28
import org.gvsig.expressionevaluator.Expression;
29
import org.gvsig.expressionevaluator.swing.ExpressionEvaluatorSwingLocator;
30
import org.gvsig.expressionevaluator.swing.ExpressionEvaluatorSwingManager;
31
import org.gvsig.expressionevaluator.swing.ExpressionPickerController;
32
import org.gvsig.fmap.dal.DALLocator;
33
import org.gvsig.fmap.dal.exception.DataException;
34
import org.gvsig.fmap.dal.expressionevaluator.FeatureAttributeEmulatorExpression;
35
import org.gvsig.fmap.dal.feature.EditableFeatureAttributeDescriptor;
36
import org.gvsig.fmap.dal.feature.FeatureAttributeDescriptor;
37
import org.gvsig.fmap.dal.feature.FeatureQuery;
38
import org.gvsig.fmap.dal.feature.FeatureStore;
39
import org.gvsig.fmap.dal.feature.FeatureType;
40
import org.gvsig.fmap.dal.swing.DALSwingLocator;
41
import org.gvsig.fmap.dal.swing.featurequery.FeatureQueryCalculatedColumnsPanel;
42
import org.gvsig.fmap.dal.swing.featuretype.FeatureTypeAttributePanel;
43
import org.gvsig.fmap.dal.swing.featuretype.FeatureTypePanel;
44
import org.gvsig.tools.ToolsLocator;
45
import org.gvsig.tools.dataTypes.Coercion;
46
import org.gvsig.tools.dataTypes.CoercionException;
47
import org.gvsig.tools.dataTypes.DataType;
48
import org.gvsig.tools.dataTypes.DataTypes;
49
import org.gvsig.tools.i18n.I18nManager;
50
import org.gvsig.tools.locator.ReferenceNotRegisteredException;
51
import org.gvsig.tools.swing.api.ListElement;
52
import org.gvsig.tools.swing.api.ToolsSwingLocator;
53
import org.gvsig.tools.swing.api.ToolsSwingManager;
54
import org.gvsig.tools.swing.api.pickercontroller.DataTypePickerController;
55
import org.gvsig.tools.swing.api.threadsafedialogs.ThreadSafeDialogsManager;
56
import org.gvsig.tools.swing.api.windowmanager.Dialog;
57
import org.gvsig.tools.swing.api.windowmanager.WindowManager;
58
import org.gvsig.tools.swing.api.windowmanager.WindowManager_v2;
59
import org.gvsig.tools.swing.icontheme.IconTheme;
60
import org.gvsig.tools.util.ToolsUtilLocator;
61
import org.slf4j.Logger;
62
import org.slf4j.LoggerFactory;
63

    
64
/**
65
 *
66
 * @author jjdelcerro
67
 */
68
public class DefaultFeatureQueryCalculatedColumnsPanel
69
        extends DefaultFeatureQueryCalculatedColumnsPanelView
70
        implements FeatureQueryCalculatedColumnsPanel {
71
    
72
    private class AttributeListElement extends ListElement<FeatureAttributeDescriptor> {
73
        
74
        public AttributeListElement(FeatureAttributeDescriptor value) {
75
            super(value.getLabel(), value);
76
        }
77
        
78
        @Override
79
        public String getLabel() {
80
            return ((FeatureAttributeDescriptor) this.getValue()).getName();
81
        }
82
        
83
    }
84

    
85
    private class ColumnController implements DocumentListener, ChangeListener, ActionListener {
86

    
87
        private final JTextComponent txtName;
88
        private final JComboBox cboDataType;
89
        private final JButton btnDataType;
90
        private final JButton btnExpressionBookmarks;
91
        private final JButton btnExpressionHistory;
92
        private final JButton btnExpression;
93
        private final JTextComponent txtExpression;
94
        private ExpressionPickerController expPicker;
95
        private DataTypePickerController pickerDataType;
96
        private boolean hasChanges;
97
        private final JTextComponent txtSize;
98
        private final JTextComponent txtPrecision;
99
        private final JTextComponent txtScale;
100
        
101
        private final Logger LOGGER = LoggerFactory.getLogger(ColumnController.class);
102
        private final JButton btnColumnMore;
103
        private final JButton btnApplyChanges;
104

    
105
        public ColumnController(
106
                JTextComponent txtName,
107
                JComboBox cboDataType,
108
                JButton btnDataType,
109
                JTextComponent txtExpression,
110
                JButton btnExpression,
111
                JButton btnExpressionHistory,
112
                JButton btnExpressionBookmarks,
113
                JTextComponent txtSize,
114
                JTextComponent txtPrecision,
115
                JTextComponent txtScale,
116
                JButton btnApplyChanges,
117
                JButton btnColumnMore
118
        ) {
119
            this.txtName = txtName;
120
            this.cboDataType = cboDataType;
121
            this.btnDataType = btnDataType;
122
            this.txtExpression = txtExpression;
123
            this.btnExpression = btnExpression;
124
            this.btnExpressionHistory = btnExpressionHistory;
125
            this.btnExpressionBookmarks = btnExpressionBookmarks;
126
            this.txtSize = txtSize;
127
            this.txtPrecision = txtPrecision;
128
            this.txtScale = txtScale;
129
            this.btnApplyChanges = btnApplyChanges;
130
            this.btnColumnMore = btnColumnMore;
131
            this.hasChanges = false;
132
            this.initComponents();
133
            this.setEnabled(false);
134
        }
135

    
136
        public void initComponents() {
137
            this.pickerDataType = ToolsSwingLocator.getToolsSwingManager().createDataTypePickerController(this.cboDataType, this.btnDataType, false);
138

    
139
            ExpressionEvaluatorSwingManager managerExpSwing = ExpressionEvaluatorSwingLocator.getManager();
140
            this.expPicker = managerExpSwing.createExpressionPickerController(
141
                    txtExpression,
142
                    btnExpression,
143
                    btnExpressionBookmarks,
144
                    btnExpressionHistory
145
            );
146
            
147

    
148
            this.txtName.getDocument().addDocumentListener(this);
149
            this.cboDataType.addActionListener(this);
150
            this.txtExpression.getDocument().addDocumentListener(this);
151
            this.txtSize.getDocument().addDocumentListener(this);
152
            this.txtPrecision.getDocument().addDocumentListener(this);
153
            this.txtScale.getDocument().addDocumentListener(this);
154
            //Todo: que el listener expresion lo gestion el picker
155
            
156
            this.cboDataType.addActionListener(new ActionListener() {
157
                @Override
158
                public void actionPerformed(ActionEvent ae) {
159
                    doSetDefaultValuesForDataType();
160
                    doEnabledByDataType();
161
                }
162
            });
163

    
164
        }
165
        
166
        public void doEnabledByDataType() {
167
            JComboBox comboBox = cboDataType;
168
            if (comboBox.getSelectedItem()==null) {
169
                return;
170
            }
171
            DataType dataType = (DataType) comboBox.getSelectedItem();
172
            txtSize.setEnabled(dataType.supportSize());
173
            txtPrecision.setEnabled(dataType.supportPrecision());
174
            txtScale.setEnabled(dataType.supportScale());
175
        }
176
        
177
        public void doSetDefaultValuesForDataType() {
178
            if (this.cboDataType.getSelectedItem()==null) {
179
                return;
180
            }
181
            DataType dataType = (DataType) this.cboDataType.getSelectedItem();
182
            if (dataType.supportSize() && txtSize.getText().isEmpty()) {
183
                txtSize.setText(String.valueOf(dataType.getDefaultSize()));
184
            } else if (!dataType.supportSize()) {
185
                txtSize.setText("");
186
            }
187

    
188
            if (dataType.supportPrecision() && txtPrecision.getText().isEmpty()) {
189
                txtPrecision.setText(String.valueOf(dataType.getDefaultPrecision()));
190
            } else if (!dataType.supportPrecision()) {
191
                txtPrecision.setText("");
192
            }
193

    
194
            if (dataType.supportScale() && txtScale.getText().isEmpty()) {
195
                txtScale.setText(String.valueOf(dataType.getDefaultScale()));
196
            } else if (!dataType.supportScale()) {
197
                txtScale.setText("");
198
            }
199
        }
200

    
201
        public boolean hasChanges() {
202
            return this.hasChanges;
203
        }
204

    
205
        public void setEnabled(boolean enabled) {
206
            this.txtName.setEnabled(enabled);
207
            this.expPicker.setEnabled(enabled);
208
            this.cboDataType.setEnabled(enabled);
209
            this.txtSize.setEnabled(enabled);
210
            this.txtPrecision.setEnabled(enabled);
211
            this.txtScale.setEnabled(enabled);
212
            this.btnApplyChanges.setEnabled(enabled);
213
            this.btnColumnMore.setEnabled(enabled);
214
        }
215

    
216
        public void clean() {
217
            this.txtName.setText("");
218
            this.expPicker.set(null);
219
            this.cboDataType.setSelectedIndex(0);
220
            this.txtSize.setText("");
221
            this.txtPrecision.setText("");
222
            this.txtScale.setText("");
223
            this.btnApplyChanges.setEnabled(false);
224
            this.btnColumnMore.setEnabled(false);
225
            this.hasChanges = false;
226

    
227
        }
228

    
229
        public void put(EditableFeatureAttributeDescriptor attr) {
230
            this.clean();
231
            this.txtName.setText(attr.getName());
232
            FeatureAttributeEmulatorExpression emu = (FeatureAttributeEmulatorExpression) attr.getFeatureAttributeEmulator();
233
            if (emu != null) {
234
                try {
235
                    this.expPicker.set(emu.getExpression().clone());
236
                } catch (CloneNotSupportedException ex) {
237
                    LOGGER.warn("Not able to clone expression.", ex);
238
                    throw new RuntimeException(ex);
239
                }
240
            }
241
            this.pickerDataType.set(attr.getDataType());
242
            Coercion coerceString = ToolsLocator.getDataTypesManager().get(DataTypes.STRING).getCoercion();
243
            txtSize.setEnabled(attr.getDataType().supportSize());
244
            if (attr.getDataType().supportSize()) {
245
                try {
246
                    this.txtSize.setText((String) coerceString.coerce(attr.getSize()));
247
                } catch (CoercionException ex) {
248
                    LOGGER.warn("Not able to coerce text to integer from size box.", ex);
249
                }
250
            }
251
            txtPrecision.setEnabled(attr.getDataType().supportPrecision());
252
            if (attr.getDataType().supportPrecision()) {
253
                try {
254
                    this.txtPrecision.setText((String) coerceString.coerce(attr.getPrecision()));
255
                } catch (CoercionException ex) {
256
                    LOGGER.warn("Not able to coerce text to integer from precision box.", ex);
257
                }
258
            }
259
            txtScale.setEnabled(attr.getDataType().supportScale());
260
            if (attr.getDataType().supportScale()) {
261
                try {
262
                    this.txtScale.setText((String) coerceString.coerce(attr.getScale()));
263
                } catch (CoercionException ex) {
264
                    LOGGER.warn("Not able to coerce text to integer from scale box.", ex);
265
                }
266
            }
267
//            doEnabledByDataType();
268
            this.btnColumnMore.setEnabled(true);
269
            this.btnApplyChanges.setEnabled(false);
270
            this.hasChanges = false;
271
        }
272

    
273
        public EditableFeatureAttributeDescriptor fetch(EditableFeatureAttributeDescriptor attr) {
274
            attr.setName(this.txtName.getText());
275
            try {
276
                Expression exp = this.expPicker.get();
277
                if (exp!=null) {
278
                    attr.setFeatureAttributeEmulator(exp.clone());
279
                } else {
280
                    attr.setFeatureAttributeEmulator((Expression) null);
281
                }
282
            } catch (CloneNotSupportedException ex) {
283
                LOGGER.warn("Not able to clone expression.", ex);
284
                throw new RuntimeException(ex);
285
            }
286
            attr.setDataType(this.pickerDataType.get());
287
            Coercion coerceInteger = ToolsLocator.getDataTypesManager().get(DataTypes.INTEGER).getCoercion();
288
            try {
289
                if (attr.getDataType().supportSize()) {
290
                    attr.setSize((int) coerceInteger.coerce(this.txtSize.getText()));
291
                }
292
            } catch (CoercionException ex) {
293
                LOGGER.warn("Not able to coerce text to integer from size box.", ex);
294
            }
295
            try {
296
                if (attr.getDataType().supportPrecision()) {
297
                    attr.setPrecision((int) coerceInteger.coerce(this.txtPrecision.getText()));
298
                }
299
            } catch (CoercionException ex) {
300
                LOGGER.warn("Not able to coerce text to integer from precision box.", ex);
301
            }
302
            try {
303
                if (attr.getDataType().supportScale()) {
304
                    attr.setScale((int) coerceInteger.coerce(this.txtScale.getText()));
305
                }
306
            } catch (CoercionException ex) {
307
                LOGGER.warn("Not able to coerce text to integer from scale box.", ex);
308
            }
309
            this.hasChanges = false;
310
            this.btnColumnMore.setEnabled(true);
311
            this.btnApplyChanges.setEnabled(false);
312
            return attr;
313
        }
314

    
315
        private void doHasChanges() {
316
            this.btnApplyChanges.setEnabled(true);
317
            this.hasChanges = true;
318
        }
319

    
320
        @Override
321
        public void insertUpdate(DocumentEvent de) {
322
            doHasChanges();
323
        }
324

    
325
        @Override
326
        public void removeUpdate(DocumentEvent de) {
327
            doHasChanges();
328
        }
329

    
330
        @Override
331
        public void changedUpdate(DocumentEvent de) {
332
            doHasChanges();
333
        }
334

    
335
        @Override
336
        public void stateChanged(ChangeEvent ce) {
337
            doHasChanges();
338
        }
339

    
340
        @Override
341
        public void actionPerformed(ActionEvent ae) {
342
            doHasChanges();
343
        }
344
        
345
        public void setStore(FeatureStore store) {
346
          DALSwingLocator.getManager().configureExpressionBuilder(expPicker, store);
347
//             FeatureStoreElement calculatedStoreElement = DALSwingLocator.getSwingManager()
348
//                    .createFeatureStoreElement();
349
//            calculatedStoreElement.setFeatureStore(store);
350
//            this.expPicker.removeAllSymbolTables();
351
//            this.expPicker.addElement(calculatedStoreElement);
352
        }
353
    }
354

    
355
    private ColumnController columnController;
356
    private FeatureStore store;
357
    private FeatureType featureType;
358
    private FeatureQuery query;
359
//    private JExpressionBuilder pckExpression;
360
    private static final String COLUMN_DEFAULT_NAME = "Field";
361
    private EditableFeatureAttributeDescriptor actualEditableAttribute;
362
    private DefaultListModel lstAttributesModel;
363
    private static final Logger LOGGER = LoggerFactory.getLogger(DefaultFeatureQueryCalculatedColumnsPanel.class);
364

    
365
    public DefaultFeatureQueryCalculatedColumnsPanel() {
366
        this.columnController = null;
367
        this.initComponents();
368
    }
369

    
370
    @Override
371
    public JComponent asJComponent() {
372
        return this;
373
    }
374

    
375
    @Override
376
    public ImageIcon loadImage(String imageName) {
377
        String name = FilenameUtils.getBaseName(imageName);
378
        IconTheme theme = ToolsSwingLocator.getIconThemeManager().getDefault();
379
        if (theme.exists(name)) {
380
            return theme.get(name);
381
        }
382
        URL url = this.getClass().getResource(name + ".png");
383
        if (url == null) {
384
            return null;
385
        }
386
        return new ImageIcon(url);
387
    }
388

    
389
    @Override
390
    public void setStore(FeatureStore store) {
391
        try {
392
            this.featureType = store.getDefaultFeatureType();
393
            this.store = store;
394
            this.query = store.createFeatureQuery();
395
            this.columnController.setStore(store);
396
//            this.pckExpression = DALSwingLocator.getManager().createQueryFilterExpresion(store);
397
        } catch (DataException ex) {
398
            throw new RuntimeException("Can't assign store", ex);
399
        }
400
    }
401

    
402
    private void initComponents() {
403
        ToolsSwingManager toolsSwingManager = ToolsSwingLocator.getToolsSwingManager();
404

    
405
        IconTheme theme = ToolsSwingLocator.getIconThemeManager().getCurrent();
406
        ImageIcon icon = theme.get("picker-datatype");
407
        this.btnColumnDataType.setIcon(icon);
408
        toolsSwingManager.translate(this.lblExpression);
409
        toolsSwingManager.translate(this.lblName);
410
        toolsSwingManager.translate(this.lblType);
411
        toolsSwingManager.translate(this.lblSize);
412
        toolsSwingManager.translate(this.lblPrecision);
413
        toolsSwingManager.translate(this.lblScale);
414
        toolsSwingManager.translate(this.btnApplyChanges);
415
        toolsSwingManager.translate(this.btnColumnMore);
416

    
417
        this.columnController = new ColumnController(
418
                this.txtColumnName,
419
                this.cboColumnDataType,
420
                this.btnColumnDataType,
421
                this.txtColumnExpression,
422
                this.btnColumnExpression,
423
                this.btnColumnExpressionHistory,
424
                this.btnColumnExpressionBookmarks,
425
                this.txtColumnSize,
426
                this.txtColumnPrecision,
427
                this.txtColumnScale,
428
                this.btnApplyChanges,
429
                this.btnColumnMore
430
        );
431
//        this.lstAttributes.setCellRenderer(new FeatureAttributeListCellRenderer());
432

    
433
        this.lstAttributes.addListSelectionListener((ListSelectionEvent e) -> {
434
            if (e.getValueIsAdjusting()) {
435
                return;
436
            }
437
            doSelectAttribute();
438
        });
439

    
440
        Dimension sz = this.getPreferredSize();
441
        if (sz.width < DEFAULT_WIDTH) {
442
            sz.width = DEFAULT_WIDTH;
443
        }
444
        if (sz.height < DEFAULT_HEIGHT) {
445
            sz.height = DEFAULT_HEIGHT;
446
        }
447
        this.setPreferredSize(sz);
448

    
449
        this.lstAttributesModel = new DefaultListModel<ListElement<EditableFeatureAttributeDescriptor>>();
450
//        this.lstAttributesModel = ToolsSwingLocator.getToolsSwingManager().createFilteredListModel();
451
        this.lstAttributes.setModel(lstAttributesModel);
452

    
453
        this.lstAttributes.setSelectionModel(new DefaultListSelectionModel() {
454

    
455
            @Override
456
            public void setSelectionInterval(int index0, int index1) {
457
                if (checkColumnControllerHasChangesWithUser()) {
458
                    super.setSelectionInterval(index0, index1);
459
                    doSelectAttribute();
460
                }
461
            }
462

    
463
        });
464

    
465
        this.btnAdd.addActionListener((ActionEvent e) -> {
466
            if (checkColumnControllerHasChangesWithUser()) {
467
                doAdd();
468
            }
469
        });
470

    
471
        this.btnRemove.addActionListener((ActionEvent e) -> {
472
            doRemove();
473
        });
474

    
475
        this.btnUp.addActionListener((ActionEvent e) -> {
476
            doUp(lstAttributes);
477
        });
478

    
479
        this.btnDown.addActionListener((ActionEvent e) -> {
480
            doDown(lstAttributes);
481
        });
482

    
483
        this.btnApplyChanges.addActionListener((ActionEvent e) -> {
484
            doApplyChanges();
485
        });
486

    
487
        this.btnColumnMore.addActionListener((ActionEvent e) -> {
488
            doColumnMore();
489
        });
490
        
491
    }
492

    
493
    private boolean checkColumnControllerHasChangesWithUser() {
494
        if (this.hasChanges()) {
495
            I18nManager i18n = ToolsLocator.getI18nManager();
496
            String message = i18n.getTranslation("_Changes_has_not_been_saved_Are_you_sure_you_want_to_continue");
497
            String title = i18n.getTranslation("_Changes_not_saved");
498
            int r = ToolsSwingLocator.getThreadSafeDialogsManager().confirmDialog(message, title,
499
                    JOptionPane.YES_NO_OPTION,
500
                    JOptionPane.QUESTION_MESSAGE);
501
            if (r == JOptionPane.NO_OPTION) {
502
                return false;
503
            }
504

    
505
        }
506
        return true;
507
    }
508

    
509
    private void doColumnMore() {
510
        if (this.columnController == null) {
511
            return;
512
        }
513
        final I18nManager i18n = ToolsLocator.getI18nManager();
514
        WindowManager_v2 winManager = (WindowManager_v2) ToolsSwingLocator.getWindowManager();
515
        final FeatureTypeAttributePanel panel = DALSwingLocator.getSwingManager().createFeatureTypeAttributePanel();
516
        panel.clean();
517
//                panel.setNameAsNew(featureType);
518
        panel.put(actualEditableAttribute);
519
        panel.setMode(FeatureTypePanel.MODE_EDIT_ALL);
520
        final Dialog dialog = winManager.createDialog(
521
                panel.asJComponent(),
522
                i18n.getTranslation("_Extra_column"),
523
                null,
524
                WindowManager_v2.BUTTONS_OK_CANCEL
525
        );
526
        dialog.addActionListener(new ActionListener() {
527
            @Override
528
            public void actionPerformed(ActionEvent e) {
529
                if (dialog.getAction() != WindowManager_v2.BUTTONS_OK) {
530
                    return;
531
                }
532
                try {
533
                    FeatureAttributeDescriptor prev = actualEditableAttribute.getCopy();
534
                    panel.fetch(actualEditableAttribute);
535
                    columnController.put(actualEditableAttribute);
536
                    if (!prev.equals(actualEditableAttribute)) {
537
                        columnController.doHasChanges();
538
                    }
539
                } catch (Exception ex) {
540
                    LOGGER.warn("Problems updating feature descriptor.", ex);
541
                }
542
            }
543
        });
544
        dialog.show(WindowManager.MODE.DIALOG);
545
    }
546

    
547
    public boolean checkPanel(StringBuilder msg) {
548
        I18nManager i18n = ToolsLocator.getI18nManager();
549
        if (this.hasChanges()) {
550
            int r = ToolsSwingLocator.getThreadSafeDialogsManager().confirmDialog(
551
                    i18n.getTranslation("_Changes_has_not_been_saved_Are_you_sure_you_want_to_continue"),
552
                    i18n.getTranslation("_Changes_not_saved"),
553
                    JOptionPane.YES_NO_OPTION,
554
                    JOptionPane.QUESTION_MESSAGE);
555
            if (r == JOptionPane.NO_OPTION) {
556
                return false;
557
            }
558
        }
559
        return true;
560
    }
561

    
562
    public boolean hasChanges() {
563
        return this.columnController.hasChanges();
564
    }
565

    
566
    private void doSelectAttribute() {
567
        EditableFeatureAttributeDescriptor value = null;
568
        if (this.lstAttributes.getSelectedValue() != null) {
569
            ListElement<EditableFeatureAttributeDescriptor> selectedValue = (ListElement<EditableFeatureAttributeDescriptor>) this.lstAttributes.getSelectedValue();
570
            if (selectedValue != null) {
571
                value = selectedValue.getValue();
572
            }
573
        }
574
        if (value == null) {
575
            this.columnController.clean();
576
            this.columnController.setEnabled(false);
577
            this.actualEditableAttribute = null;
578

    
579
        } else {
580
            //EditableFeatureAttributeDescriptor value = node.getValue();
581
            this.actualEditableAttribute = value;
582
            columnController.setEnabled(true);
583
            columnController.put(value);
584
        }
585
    }
586

    
587
    @Override
588
    public FeatureQuery fetch(FeatureQuery query) {
589
        if (hasChanges()) {
590
            I18nManager i18n = ToolsLocator.getI18nManager();
591
            String message = i18n.getTranslation("_Changes_has_not_been_saved_Do_you_want_to_save_them_before_continue");
592
            String title = i18n.getTranslation("_Changes_not_saved");
593
            int r = ToolsSwingLocator.getThreadSafeDialogsManager().confirmDialog(message, title,
594
                    JOptionPane.YES_NO_OPTION,
595
                    JOptionPane.QUESTION_MESSAGE);
596
            if (r == JOptionPane.YES_NO_OPTION) {
597
                doApplyChanges();
598
            }
599
        }
600
        
601
        if (query == null) {
602
            return this.query.getCopy();
603
        }
604

    
605
        this.query.getExtraColumn().clear();
606
        for (int i = 0; i < lstAttributesModel.getSize(); i++) {
607
            ListElement<EditableFeatureAttributeDescriptor> element = (ListElement<EditableFeatureAttributeDescriptor>) lstAttributesModel.get(i);
608
            EditableFeatureAttributeDescriptor newExtraColumn = this.query.getExtraColumn().add(element.getValue().getName(), element.getValue().getType());
609
            newExtraColumn.copyFrom(element.getValue());
610
        }
611
        query.copyFrom(this.query);
612

    
613
        return query;
614
    }
615

    
616
    @Override
617
    public FeatureQuery fetch() {
618
        return this.fetch(null);
619
    }
620

    
621
    @Override
622
    public void put(FeatureQuery query) {
623
        this.query.copyFrom(query);
624
        addExtraColumns(this.query);
625
    }
626

    
627
    private void addExtraColumns(FeatureQuery query) {
628
        List<EditableFeatureAttributeDescriptor> cols = query.getExtraColumn().getColumns();
629
        if (cols == null || cols.isEmpty()) {
630
            return;
631
        }
632
        for (EditableFeatureAttributeDescriptor col : cols) {
633
            ListElement lf = new AttributeListElement(col);
634
            this.lstAttributesModel.addElement(lf);
635
        }
636
        if (this.lstAttributesModel.getSize() > 0) {
637
            this.lstAttributes.setSelectedIndex(0);
638
        }
639
    }
640

    
641
    public static void selfRegister() {
642
        IconTheme theme;
643
        try {
644
           theme = ToolsSwingLocator.getIconThemeManager().getCurrent();
645
        } catch(ReferenceNotRegisteredException ex) {
646
            return;
647
        }
648
        String[][] iconNames = new String[][]{
649
            new String[]{"dalswing", "featurequery-column-add"},
650
            new String[]{"dalswing", "featurequery-column-remove"},
651
            new String[]{"dalswing", "featurequery-column-down"},
652
            new String[]{"dalswing", "featurequery-column-up"}
653
        };
654
        for (String[] icon : iconNames) {
655
            URL url = DefaultFeatureQueryOrderPanel.class.getResource(icon[1] + ".png");
656
            theme.registerDefault("DALSwing", icon[0], icon[1], null, url);
657
        }
658
    }
659

    
660
    private void doAdd() {
661
        int id = 0;
662
        String newName = COLUMN_DEFAULT_NAME;
663
        while (checkIfValueExistInModel(newName, this.lstAttributesModel)) {
664
            newName = COLUMN_DEFAULT_NAME + "_" + id;
665
            id += 1;
666
        }
667
        EditableFeatureAttributeDescriptor newAttr = DALLocator.getDataManager().createFeatureAttributeDescriptor(
668
                newName,
669
                DataTypes.STRING
670
        );
671
        if (newAttr.getDataType().supportSize()) {
672
            newAttr.setSize(newAttr.getDataType().getDefaultSize());
673
        }
674
        this.columnController.put(newAttr);
675
        this.columnController.setEnabled(true);
676

    
677
        this.lstAttributesModel.addElement(new AttributeListElement(newAttr));
678
        ListElement.setSelected(this.lstAttributes, newAttr);
679
        this.lstAttributes.revalidate();
680
        this.lstAttributes.repaint();
681
        this.actualEditableAttribute = newAttr;
682

    
683
    }
684

    
685
    private boolean checkIfValueExistInModel(String name, ListModel<ListElement<EditableFeatureAttributeDescriptor>> model) {
686
        for (int i = 0; i < model.getSize(); i++) {
687
            EditableFeatureAttributeDescriptor element = model.getElementAt(i).getValue();
688
            if (StringUtils.equals(element.getLabel(), name)) {
689
                return true;
690
            }
691

    
692
        }
693
        return false;
694
    }
695

    
696
    private void doRemove() {
697
        AttributeListElement selectedValue = (AttributeListElement) this.lstAttributes.getSelectedValue();
698
        if( selectedValue == null ) {
699
            return;
700
        }
701
        FeatureAttributeDescriptor attr = selectedValue.getValue();
702
        if( attr == null ) {
703
            return;
704
        }
705
        boolean removeFromAggregateFunctions = false;
706
        boolean removeFromOrder = false;
707
        boolean removeFromGroupByColums = false;
708
        if( this.query.getAggregateFunctions().containsKey(attr.getName()) ) {
709
            ThreadSafeDialogsManager dialogs = ToolsSwingLocator.getThreadSafeDialogsManager();
710
            int n = dialogs.confirmDialog(
711
                    "El campo '"+attr.getName()+"' se esta usando en una funcion de agregado. ? Dese borrarlo igualmente ?", 
712
                    "Eliminar campo", 
713
                    JOptionPane.YES_NO_OPTION, 
714
                    JOptionPane.QUESTION_MESSAGE, 
715
                    "_FeatureQueryCalculatedColumns_remove_used_column"
716
            );
717
            if( n != JOptionPane.YES_OPTION ) {
718
                return;
719
            }
720
            n = dialogs.confirmDialog(
721
                    "? Desea eliminar la funcion de agregado donde se esta usando el campo '"+attr.getName()+"' ?", 
722
                    "Eliminar campo", 
723
                    JOptionPane.YES_NO_OPTION, 
724
                    JOptionPane.QUESTION_MESSAGE, 
725
                    "_FeatureQueryCalculatedColumns_remove_aggregate_function_when_remove_column"
726
            );
727
            if( n == JOptionPane.YES_OPTION ) {
728
                removeFromAggregateFunctions = true;
729
            }
730
        }
731
        if( this.query.getGroupByColumns().contains(attr.getName()) ) {
732
            ThreadSafeDialogsManager dialogs = ToolsSwingLocator.getThreadSafeDialogsManager();
733
            int n = dialogs.confirmDialog(
734
                    "El campo '"+attr.getName()+"' se esta usando como campo de agrupacion. ? Dese borrarlo igualmente ?", 
735
                    "Eliminar campo", 
736
                    JOptionPane.YES_NO_OPTION, 
737
                    JOptionPane.QUESTION_MESSAGE, 
738
                    "_FeatureQueryCalculatedColumns_remove_used_column"
739
            );
740
            if( n != JOptionPane.YES_OPTION ) {
741
                return;
742
            }
743
            n = dialogs.confirmDialog(
744
                    "? Desea eliminar la agrupacion por el campo '"+attr.getName()+"' ?", 
745
                    "Eliminar campo", 
746
                    JOptionPane.YES_NO_OPTION, 
747
                    JOptionPane.QUESTION_MESSAGE, 
748
                    "_FeatureQueryCalculatedColumns_remove_group_by_column_when_remove_column"
749
            );
750
            if( n == JOptionPane.YES_OPTION ) {
751
                removeFromGroupByColums = true;
752
            }
753
        }
754
        if( this.query.getOrder().contains(attr.getName()) ) {
755
            ThreadSafeDialogsManager dialogs = ToolsSwingLocator.getThreadSafeDialogsManager();
756
            int n = dialogs.confirmDialog(
757
                    "El campo '"+attr.getName()+"' se esta usando para establecer el orden. ? Dese borrarlo igualmente ?", 
758
                    "Eliminar campo", 
759
                    JOptionPane.YES_NO_OPTION, 
760
                    JOptionPane.QUESTION_MESSAGE, 
761
                    "_FeatureQueryCalculatedColumns_remove_used_column"
762
            );
763
            if( n != JOptionPane.YES_OPTION ) {
764
                return;
765
            }
766

    
767
            n = dialogs.confirmDialog(
768
                    "? Desea eliminar el uso del campo '"+attr.getName()+"' en la ordenacion ?", 
769
                    "Eliminar campo", 
770
                    JOptionPane.YES_NO_OPTION, 
771
                    JOptionPane.QUESTION_MESSAGE, 
772
                    "_FeatureQueryCalculatedColumns_remove_order_when_remove_column"
773
            );
774
            if( n == JOptionPane.YES_OPTION ) {
775
                removeFromOrder = true;
776
            }
777
        }
778
        if( removeFromAggregateFunctions ) {
779
           this.query.removeAggregateFunction(attr.getName());
780
        }
781
        if( removeFromOrder ) {
782
            int index = this.query.getOrder().getIndex(attr.getName());
783
            this.query.getOrder().remove(index);
784
        }
785
        if( removeFromGroupByColums ) {
786
            this.query.removeGroupByColumn(attr.getName());
787
        }
788
        
789
        ListSelectionModel lsm = lstAttributes.getSelectionModel();
790
        DefaultListModel model = (DefaultListModel) this.lstAttributes.getModel();
791
        int actualIndex = lsm.getMinSelectionIndex();
792
        this.lstAttributesModel.removeElement(selectedValue);
793
        this.columnController.clean();
794

    
795
        int size = model.size();
796
        if (size == 0) {
797
            //List is empty: disable delete, up, and down buttons.
798
        } else {
799
            //Adjust the selection.
800
            if (model.getSize() == 0) {
801

    
802
            } else if (actualIndex >= model.getSize()) {
803
                lstAttributes.setSelectedIndex(model.getSize() - 1);
804
            } else {
805
                lstAttributes.setSelectedIndex(actualIndex);
806
            }
807
        }
808
    }
809

    
810
    private void doApplyChanges() {
811
        this.columnController.fetch(this.actualEditableAttribute);
812
        this.lstAttributes.invalidate();
813
        this.lstAttributes.repaint();
814
    }
815

    
816
    private void doUp(JList lstColumns) {
817
        int moveMe = lstColumns.getSelectedIndex();
818
        if (moveMe != 0) {
819
            //not already at top
820
            swap(lstColumns, moveMe, moveMe - 1);
821
            lstColumns.setSelectedIndex(moveMe - 1);
822
            lstColumns.ensureIndexIsVisible(moveMe - 1);
823
        }
824
    }
825

    
826
    private void doDown(JList lstColumns) {
827
        int moveMe = lstColumns.getSelectedIndex();
828
        if (moveMe != lstColumns.getModel().getSize() - 1) {
829
            //not already at bottom
830
            swap(lstColumns, moveMe, moveMe + 1);
831
            lstColumns.setSelectedIndex(moveMe + 1);
832
            lstColumns.ensureIndexIsVisible(moveMe + 1);
833
        }
834
    }
835

    
836
    private void swap(JList lstColumns, int a, int b) {
837
        DefaultListModel model = (DefaultListModel) lstColumns.getModel();
838
        Object aObject = model.getElementAt(a);
839
        Object bObject = model.getElementAt(b);
840
        model.set(a, bObject);
841
        model.set(b, aObject);
842
    }
843
}