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 / searchpanel / DefaultSearchPanel.java @ 44262

History | View | Annotate | Download (16.6 KB)

1
package org.gvsig.fmap.dal.swing.impl.searchpanel;
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.ArrayList;
8
import java.util.List;
9
import javax.swing.ImageIcon;
10
import javax.swing.JComponent;
11
import javax.swing.SwingUtilities;
12
import javax.swing.event.ListSelectionEvent;
13
import javax.swing.event.ListSelectionListener;
14
import javax.swing.table.AbstractTableModel;
15
import javax.swing.table.TableModel;
16
import org.apache.commons.io.FilenameUtils;
17
import org.apache.commons.lang.mutable.MutableLong;
18
import org.apache.commons.lang.mutable.MutableObject;
19
import org.gvsig.expressionevaluator.Expression;
20
import org.gvsig.expressionevaluator.ExpressionBuilder;
21
import static org.gvsig.expressionevaluator.ExpressionBuilder.OPERATOR_AND;
22
import static org.gvsig.expressionevaluator.ExpressionBuilder.OPERATOR_OR;
23
import org.gvsig.expressionevaluator.ExpressionUtils;
24
import org.gvsig.expressionevaluator.swing.ExpressionEvaluatorSwingLocator;
25
import org.gvsig.expressionevaluator.swing.ExpressionEvaluatorSwingManager;
26
import org.gvsig.expressionevaluator.swing.ExpressionPickerController;
27
import org.gvsig.featureform.swing.JFeaturesForm;
28
import org.gvsig.fmap.dal.complements.Search;
29
import org.gvsig.fmap.dal.exception.DataException;
30
import org.gvsig.fmap.dal.feature.Feature;
31
import org.gvsig.fmap.dal.feature.FeatureAttributeDescriptor;
32
import org.gvsig.fmap.dal.feature.FeatureQuery;
33
import org.gvsig.fmap.dal.feature.FeatureStore;
34
import org.gvsig.fmap.dal.feature.FeatureType;
35
import org.gvsig.fmap.dal.swing.DALSwingLocator;
36
import org.gvsig.fmap.dal.swing.DataSwingManager;
37
import org.gvsig.fmap.dal.swing.searchpanel.FeatureStoreSearchPanel;
38
import org.gvsig.tools.ToolsLocator;
39
import org.gvsig.tools.swing.api.ActionListenerSupport;
40
import org.gvsig.tools.swing.api.ToolsSwingLocator;
41
import org.gvsig.tools.swing.api.windowmanager.WindowManager;
42
import org.gvsig.tools.swing.icontheme.IconTheme;
43
import org.slf4j.Logger;
44
import org.slf4j.LoggerFactory;
45

    
46
/**
47
 *
48
 * @author jjdelcerro
49
 */
50
@SuppressWarnings("UseSpecificCatch")
51
public class DefaultSearchPanel
52
        extends DefaultSearchPanelView
53
        implements FeatureStoreSearchPanel {
54

    
55
    private static final Logger LOGGER = LoggerFactory.getLogger(DefaultSearchPanel.class);
56
    private boolean showFormSingleElement;
57
    private Expression currentSearch;
58

    
59
    private class FeaturesTableModel extends AbstractTableModel {
60

    
61
        private final List<Feature> features;
62
        private final List<String> columnNames;
63
        private final FeatureType featureType;
64

    
65
        public FeaturesTableModel(FeatureType featureType, List<String> columnNames, List<Feature> features) {
66
            this.features = features;
67
            this.featureType = featureType;
68
            if (columnNames == null || columnNames.isEmpty()) {
69
                this.columnNames = new ArrayList<>();
70
                Search search = (Search) ToolsLocator.getComplementsManager().get(
71
                        Search.COMPLEMENT_MANE, featureType
72
                );
73
                List<FeatureAttributeDescriptor> attributos = search.getOrderedAttributes(
74
                        Search.BASIC_TYPES_FILTER,
75
                        Search.STR_INT_LONG_LABEL_ORDER,
76
                        12
77
                );
78
                for (FeatureAttributeDescriptor attrdesc : attributos) {
79
                    this.columnNames.add(attrdesc.getName());
80
                }
81
            } else {
82
                this.columnNames = columnNames;
83
            }
84
        }
85

    
86
        public List<Feature> getFeatures() {
87
            return this.features;
88
        }
89

    
90
        @Override
91
        public int getRowCount() {
92
            if (this.features == null) {
93
                return 0;
94
            }
95
            return this.features.size();
96
        }
97

    
98
        @Override
99
        public int getColumnCount() {
100
            return this.columnNames.size();
101
        }
102

    
103
        @Override
104
        public String getColumnName(int columnIndex) {
105
            String attrName = this.columnNames.get(columnIndex);
106
            if (this.featureType == null) {
107
                return attrName;
108
            }
109
            FeatureAttributeDescriptor attrdesc = this.featureType.getAttributeDescriptor(attrName);
110
            if (attrdesc == null) {
111
                return "C" + columnIndex;
112
            }
113
            return attrdesc.getLabel();
114
        }
115

    
116
        @Override
117
        public Class<?> getColumnClass(int columnIndex) {
118
            if (this.featureType == null) {
119
                return String.class;
120
            }
121
            String attrName = this.columnNames.get(columnIndex);
122
            FeatureAttributeDescriptor attrdesc = this.featureType.getAttributeDescriptor(attrName);
123
            if (attrdesc == null) {
124
                return String.class;
125
            }
126
            return attrdesc.getDataType().getDefaultClass();
127
        }
128

    
129
        @Override
130
        public boolean isCellEditable(int rowIndex, int columnIndex) {
131
            return false;
132
        }
133

    
134
        @Override
135
        public Object getValueAt(int rowIndex, int columnIndex) {
136
            if (this.features == null) {
137
                return null;
138
            }
139
            Feature feature = this.features.get(rowIndex);
140
            String attrName = this.columnNames.get(columnIndex);
141
            try {
142
                return feature.get(attrName);
143
            } catch (Throwable th) {
144
                return null;
145
            }
146
        }
147

    
148
        @Override
149
        public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
150

    
151
        }
152
    }
153

    
154
    private final FeatureStore store;
155
    private final ActionListenerSupport acctionListeners;
156
    private final List<SearchFieldController> searchFields;
157
    private ExpressionPickerController advancedExpression;
158

    
159
    public DefaultSearchPanel(FeatureStore store) {
160
        this.store = store;
161
        this.acctionListeners = ToolsSwingLocator.getToolsSwingManager().createActionListenerSupport();
162
        this.searchFields = new ArrayList<>();
163
        this.initComponents();
164
    }
165

    
166
    @Override
167
    public JComponent asJComponent() {
168
        return this;
169
    }
170

    
171
    @Override
172
    public void addActionListener(ActionListener listener) {
173
        this.acctionListeners.addActionListener(listener);
174
    }
175

    
176
    @Override
177
    public ActionListener[] getActionListeners() {
178
        return this.acctionListeners.getActionListeners();
179
    }
180

    
181
    @Override
182
    public void removeActionListener(ActionListener listener) {
183
        this.acctionListeners.removeActionListener(listener);
184
    }
185

    
186
    @Override
187
    public void removeAllActionListener() {
188
        this.acctionListeners.removeAllActionListener();
189
    }
190

    
191
    @Override
192
    public void fireActionEvent(ActionEvent event) {
193
        this.acctionListeners.fireActionEvent(event);
194
    }
195

    
196
    @Override
197
    public boolean hasActionListeners() {
198
        return this.acctionListeners.hasActionListeners();
199
    }
200

    
201
    private void initComponents() {
202
        SearchFieldController controller = new SearchFieldController(
203
                store,
204
                lblField1,
205
                lblExtraFields1,
206
                lblRelationalOperator1,
207
                cboValue1,
208
                lblLogicalOperators1
209
        );
210
        this.searchFields.add(controller);
211
        controller = new SearchFieldController(
212
                store,
213
                lblField2,
214
                lblExtraFields2,
215
                lblRelationalOperator2,
216
                cboValue2,
217
                lblLogicalOperators2
218
        );
219
        this.searchFields.add(controller);
220
        controller = new SearchFieldController(
221
                store,
222
                lblField3,
223
                lblExtraFields3,
224
                lblRelationalOperator3,
225
                cboValue3,
226
                lblLogicalOperators3
227
        );
228
        this.searchFields.add(controller);
229
        controller = new SearchFieldController(
230
                store,
231
                lblField4,
232
                lblExtraFields4,
233
                lblRelationalOperator4,
234
                cboValue4,
235
                null
236
        );
237
        this.searchFields.add(controller);
238
        try {
239
            Search search = (Search) ToolsLocator.getComplementsManager().get(
240
                    Search.COMPLEMENT_MANE, this.store.getDefaultFeatureType()
241
            );
242
            List<FeatureAttributeDescriptor> orderedAttributes = search.getOrderedAttributes(
243
                    Search.BASIC_TYPES_FILTER,
244
                    Search.STR_INT_LONG_LABEL_ORDER,
245
                    5
246
            );
247
            int n = 0;
248
            for (SearchFieldController searchField : searchFields) {
249
                searchField.setAttribute(orderedAttributes.get(n++).getName());
250
            }
251
        } catch (DataException ex) {
252
            LOGGER.warn("Can't determine order of attributes", ex);
253
        }
254

    
255
        ExpressionEvaluatorSwingManager expressionSwingManager = ExpressionEvaluatorSwingLocator.getManager();
256
        this.advancedExpression = expressionSwingManager.createExpressionPickerController(txtAdvancedExpression, btnAdvancedExpression);
257

    
258
        this.btnSearch.addActionListener(new ActionListener() {
259
            @Override
260
            public void actionPerformed(ActionEvent e) {
261
                doSearch();
262
            }
263
        });
264

    
265
        this.btnShowForm.addActionListener(new ActionListener() {
266
            @Override
267
            public void actionPerformed(ActionEvent e) {
268
                doShowForm();
269
            }
270
        });
271
        try {
272
            this.showFormSingleElement = true;
273
            FeatureAttributeDescriptor[] pks = this.store.getDefaultFeatureType().getPrimaryKey();
274
            if (pks == null || pks.length < 1) {
275
                this.showFormSingleElement = false;
276
            }
277
        } catch (Exception ex) {
278
        }
279
        this.btnShowForm.setEnabled(true);
280

    
281
        this.tblResults.getSelectionModel().addListSelectionListener(new ListSelectionListener() {
282
            @Override
283
            public void valueChanged(ListSelectionEvent e) {
284
                if (e.getValueIsAdjusting()) {
285
                    return;
286
                }
287
                if (tblResults.getSelectedRowCount() == 0) {
288
                    btnShowForm.setEnabled(true);
289
                    return;
290
                }
291
                btnShowForm.setEnabled(showFormSingleElement);
292
            }
293
        });
294
        this.btnClear.addActionListener(new ActionListener() {
295
            @Override
296
            public void actionPerformed(ActionEvent e) {
297
                clear();
298
            }
299
        });
300
        this.setPreferredSize(new Dimension(700, 450));
301

    
302
        doSearch(null);
303
    }
304

    
305
    @Override
306
    public void setEnabled(boolean enabled) {
307
        for (SearchFieldController searchField : searchFields) {
308
            searchField.setEnabled(enabled);
309
        }
310
        this.btnClear.setEnabled(enabled);
311
        this.btnSearch.setEnabled(enabled);
312
        this.btnShowForm.setEnabled(enabled);
313
        this.advancedExpression.setEnabled(enabled);
314
    }
315

    
316
    public void clear() {
317
        for (SearchFieldController searchField : searchFields) {
318
            searchField.clear();
319
        }
320
        this.advancedExpression.set(null);
321
    }
322

    
323
    private void doSearch() {
324
        int searchMode = this.tabSearchMode.getSelectedIndex();
325
        if (searchMode == 1) { // Avanzada
326
            Expression filter = this.advancedExpression.get();
327
            if (ExpressionUtils.isPhraseEmpty(filter)) {
328
                return;
329
            }
330
            doSearch(filter);
331
            return;
332
        }
333

    
334
        ExpressionBuilder builder = ExpressionUtils.createExpressionBuilder();
335
        String relational = OPERATOR_OR;
336
        for (SearchFieldController searchField : searchFields) {
337
            if (searchField.getAttribute() != null && searchField.getValue() != null) {
338
                ExpressionBuilder.BinaryOperator cond = builder.binaryOperator(
339
                        searchField.getRelationalOperator(),
340
                        searchField.isAttributeAnExpression()
341
                        ? builder.custom(searchField.getAttribute())
342
                        : builder.column(searchField.getAttribute()),
343
                        builder.constant(searchField.getValue())
344
                );
345
                if (relational.equals(OPERATOR_AND)) {
346
                    builder.and(cond);
347
                } else {
348
                    builder.or(cond);
349
                }
350
                relational = searchField.getLogicalOperator();
351
            }
352
        }
353
        if (builder.isEmpty()) {
354
            doSearch(null);
355
            return;
356
        }
357
        this.txtAdvancedExpression.setText(builder.toString());
358
        doSearch(ExpressionUtils.createExpression(builder.toString()));
359
    }
360

    
361
    private void doSearch(final Expression exp) {
362
        final MutableObject model = new MutableObject(null);
363
        
364
        lblMsg.setText("Searching...");
365
        setEnabled(false);
366
        Thread th = new Thread(new Runnable() {
367
            @Override
368
            public void run() {
369
                try {
370
                    final List<Feature> features;
371
                    if (exp == null) {
372
                        features = store.getFeatures();
373
                    } else {
374
                        features = store.getFeatures(exp);
375
                    }
376
                    currentSearch = exp;
377
                    model.setValue( new FeaturesTableModel(
378
                            store.getDefaultFeatureType(),
379
                            null,
380
                            features
381
                        )
382
                    );
383
                } catch (DataException ex) {
384
                    LOGGER.warn("Can't get features or create table model",ex);
385
                } finally {
386
                    SwingUtilities.invokeLater(new Runnable() {
387
                        @Override
388
                        public void run() {
389
                            TableModel m = (TableModel) model.getValue();
390
                            tblResults.setModel(m);
391
                            lblMsg.setText(String.format("%d elementos", m.getRowCount()));
392
                            setEnabled(true);
393
                        }
394
                    });
395
                }
396
            }
397
        });
398
        th.start();
399
    }
400

    
401
    private void doShowForm() {
402
        try {
403
            this.btnShowForm.setEnabled(false);
404
            DataSwingManager dataSwingManager = DALSwingLocator.getSwingManager();
405

    
406
            Expression filter;
407
            int selectedRow = this.tblResults.getSelectedRow();
408
            if (selectedRow < 0) {
409
                filter = this.currentSearch;
410
            } else {
411
                List<Feature> features = ((FeaturesTableModel) this.tblResults.getModel()).getFeatures();
412
                Feature feature = features.get(selectedRow);
413

    
414
                ExpressionBuilder builder = ExpressionUtils.createExpressionBuilder();
415
                FeatureType ftype = this.store.getDefaultFeatureType();
416
                for (FeatureAttributeDescriptor attrdesc : ftype.getPrimaryKey()) {
417
                    builder.and(
418
                            builder.eq(
419
                                    builder.column(attrdesc.getName()),
420
                                    builder.constant(feature.get(attrdesc.getName()))
421
                            )
422
                    );
423
                }
424
                filter = ExpressionUtils.createExpression(builder.toString());
425
            }
426
            FeatureQuery query = store.createFeatureQuery();
427
            query.setFilter(filter);
428
            query.retrievesAllAttributes();
429
            JFeaturesForm form = dataSwingManager.createJFeaturesForm(store);
430
            form.setQuery(query);
431
            form.showForm(WindowManager.MODE.WINDOW);
432

    
433
        } catch (Exception ex) {
434
            LOGGER.warn("Can't show form", ex);
435
        } finally {
436
            this.btnShowForm.setEnabled(true);
437
        }
438
    }
439

    
440
    @Override
441
    public ImageIcon loadImage(String imageName) {
442
        String name = FilenameUtils.getBaseName(imageName);
443
        IconTheme theme = ToolsSwingLocator.getIconThemeManager().getDefault();
444
        if (theme.exists(name)) {
445
            return theme.get(name);
446
        }
447
        URL url = this.getClass().getResource(name + ".png");
448
        if (url == null) {
449
            return null;
450
        }
451
        return new ImageIcon(url);
452
    }
453

    
454
    public static void selfRegister() {
455
        String[][] iconNames = new String[][]{
456
            new String[]{"dalswing", "featurestore-column"},
457
            new String[]{"dalswing", "featurestore-foreing-key"},
458
            new String[]{"dalswing", "featurestore-table"}
459
        };
460
        IconTheme theme = ToolsSwingLocator.getIconThemeManager().getCurrent();
461
        for (String[] icon : iconNames) {
462
            URL url = DefaultSearchPanel.class.getResource(icon[1] + ".png");
463
            theme.registerDefault("DALSwing", icon[0], icon[1], null, url);
464
        }
465

    
466
    }
467
};