Statistics
| Revision:

gvsig-projects-pool / org.gvsig.topology / trunk / org.gvsig.topology / org.gvsig.topology.swing / org.gvsig.topology.swing.impl / src / main / java / org / gvsig / topology / swing / impl / DefaultJTopologyReport.java @ 760

History | View | Annotate | Download (26.5 KB)

1 688 jjdelcerro
package org.gvsig.topology.swing.impl;
2
3 722 jjdelcerro
import java.awt.BorderLayout;
4 688 jjdelcerro
import java.awt.Dimension;
5
import java.awt.event.ActionEvent;
6
import java.awt.event.ActionListener;
7 723 jjdelcerro
import java.awt.event.MouseAdapter;
8
import java.awt.event.MouseEvent;
9 727 jjdelcerro
import java.net.URL;
10
import java.util.ArrayList;
11 688 jjdelcerro
import java.util.HashSet;
12
import java.util.List;
13
import java.util.Set;
14
import javax.swing.DefaultComboBoxModel;
15 760 jjdelcerro
import javax.swing.DefaultListSelectionModel;
16 727 jjdelcerro
import javax.swing.ImageIcon;
17 688 jjdelcerro
import javax.swing.JComponent;
18
import javax.swing.JMenuItem;
19
import javax.swing.JPopupMenu;
20
import javax.swing.JTable;
21 760 jjdelcerro
import javax.swing.ListSelectionModel;
22 688 jjdelcerro
import javax.swing.SwingUtilities;
23
import javax.swing.event.ChangeEvent;
24
import javax.swing.event.ChangeListener;
25
import javax.swing.event.ListSelectionEvent;
26
import javax.swing.event.ListSelectionListener;
27
import javax.swing.event.TableModelEvent;
28
import javax.swing.event.TableModelListener;
29
import javax.swing.table.TableModel;
30 727 jjdelcerro
import org.apache.commons.io.FilenameUtils;
31 688 jjdelcerro
import org.apache.commons.lang3.StringUtils;
32
import org.gvsig.expressionevaluator.ExpressionBuilder;
33
import org.gvsig.expressionevaluator.ExpressionEvaluatorLocator;
34
import org.gvsig.fmap.dal.feature.FeatureSelection;
35
import org.gvsig.fmap.geom.Geometry;
36
import org.gvsig.fmap.geom.primitive.Envelope;
37
import org.gvsig.tools.ToolsLocator;
38 722 jjdelcerro
import org.gvsig.tools.dynform.DynFormLocator;
39 688 jjdelcerro
import org.gvsig.tools.dynform.JDynForm;
40 722 jjdelcerro
import org.gvsig.tools.dynobject.DynObject;
41 688 jjdelcerro
import org.gvsig.tools.i18n.I18nManager;
42
import org.gvsig.tools.observer.Observable;
43
import org.gvsig.tools.observer.Observer;
44
import org.gvsig.tools.swing.api.ListElement;
45
import org.gvsig.tools.swing.api.ToolsSwingLocator;
46
import org.gvsig.tools.swing.api.ToolsSwingManager;
47
import org.gvsig.tools.swing.api.task.TaskStatusController;
48 727 jjdelcerro
import org.gvsig.tools.swing.icontheme.IconTheme;
49 688 jjdelcerro
import org.gvsig.tools.task.TaskStatus;
50
import org.gvsig.topology.lib.api.TopologyLocator;
51
import org.gvsig.topology.lib.api.TopologyPlan;
52
import org.gvsig.topology.lib.api.TopologyReport;
53
import org.gvsig.topology.lib.api.TopologyReportLine;
54
import org.gvsig.topology.lib.api.TopologyReportLineSet;
55
import org.gvsig.topology.lib.api.TopologyRule;
56
import org.gvsig.topology.lib.api.TopologyRuleAction;
57
import org.gvsig.topology.lib.api.TopologyRuleFactory;
58
import org.gvsig.topology.swing.api.JTopologyReport;
59
import org.gvsig.topology.swing.api.TopologySwingLocator;
60
import org.gvsig.topology.swing.api.TopologySwingServices;
61
import org.gvsig.topology.swing.api.TopologySwingServices.WorkingAreaChangedListener;
62
import org.slf4j.Logger;
63
import org.slf4j.LoggerFactory;
64
65
/**
66
 *
67
 * @author jjdelcerro
68
 */
69
@SuppressWarnings("UseSpecificCatch")
70
public class DefaultJTopologyReport
71
        extends DefaultJTopologyReportView
72
        implements JTopologyReport {
73
74
    private static final Logger LOGGER = LoggerFactory.getLogger(DefaultJTopologyReport.class);
75 760 jjdelcerro
    private ListSelectionModel selection;
76 688 jjdelcerro
77
    private class TopologyRuleActionParametersListener implements ActionListener {
78
79
        private final TopologyRule rule;
80 727 jjdelcerro
        private final List<TopologyReportLine> lines;
81 688 jjdelcerro
        private final TopologyRuleAction action;
82
        private final JDynForm form;
83
84
        public TopologyRuleActionParametersListener(
85
                TopologyRule rule,
86 727 jjdelcerro
                List<TopologyReportLine> lines,
87 688 jjdelcerro
                TopologyRuleAction action,
88
                JDynForm form
89
        ) {
90
            this.action = action;
91 727 jjdelcerro
            this.lines = lines;
92 688 jjdelcerro
            this.rule = rule;
93
            this.form = form;
94
        }
95
96
        @Override
97
        public void actionPerformed(ActionEvent e) {
98 727 jjdelcerro
            doExecuteRuleAction(rule, lines, action, form);
99 688 jjdelcerro
        }
100
    }
101
102
    private class TopologyRuleActionListener implements ActionListener {
103
104
        private final TopologyRule rule;
105 727 jjdelcerro
        private final List<TopologyReportLine> lines;
106 688 jjdelcerro
        private final TopologyRuleAction action;
107
108
        public TopologyRuleActionListener(
109
                TopologyRule rule,
110 727 jjdelcerro
                List<TopologyReportLine> lines,
111 688 jjdelcerro
                TopologyRuleAction action
112
        ) {
113
            this.action = action;
114 727 jjdelcerro
            this.lines = lines;
115 688 jjdelcerro
            this.rule = rule;
116
        }
117
118
        @Override
119
        public void actionPerformed(ActionEvent e) {
120 760 jjdelcerro
            if (this.action.hasParameters()) {
121 727 jjdelcerro
                doShowActionParametersPanel(this.rule, this.lines, this.action);
122 722 jjdelcerro
            } else {
123 727 jjdelcerro
                doExecuteRuleAction(rule, lines, action, null);
124 722 jjdelcerro
            }
125 688 jjdelcerro
        }
126
    }
127 760 jjdelcerro
128 688 jjdelcerro
    private ReportTable linesModel;
129
    private final TopologySwingServices services;
130
    private TaskStatusController taskStatusController;
131
    private TopologyPlan plan;
132
    private WorkingAreaChangedListener workingAreaChangedListener;
133
134
    public DefaultJTopologyReport(TopologyPlan plan) {
135
        this.services = TopologySwingLocator.getTopologySwingManager().getDefaultServices();
136
        this.initComponents();
137
    }
138
139
    private void initComponents() {
140
        I18nManager i18n = ToolsLocator.getI18nManager();
141 760 jjdelcerro
        this.selection = this.tblErrors.getSelectionModel();
142 688 jjdelcerro
        this.linesModel = new ReportTable();
143 760 jjdelcerro
144 688 jjdelcerro
        this.workingAreaChangedListener = new WorkingAreaChangedListener() {
145
            @Override
146
            public void workingAreaChanged(Envelope workingArea) {
147
                doUpdateFilter();
148
            }
149
        };
150
        this.tblErrors.setModel(this.linesModel);
151
        this.tblErrors.setAutoResizeMode(JTable.AUTO_RESIZE_LAST_COLUMN);
152 760 jjdelcerro
153 727 jjdelcerro
        this.btnZoomGeometry.addActionListener(new ActionListener() {
154 688 jjdelcerro
            @Override
155
            public void actionPerformed(ActionEvent e) {
156 727 jjdelcerro
                doZoomGeometry();
157 688 jjdelcerro
            }
158
        });
159 727 jjdelcerro
        this.btnZoomError.addActionListener(new ActionListener() {
160 688 jjdelcerro
            @Override
161
            public void actionPerformed(ActionEvent e) {
162 727 jjdelcerro
                doZoomError();
163 688 jjdelcerro
            }
164
        });
165 727 jjdelcerro
        this.btnCenterGeometry.addActionListener(new ActionListener() {
166
            @Override
167
            public void actionPerformed(ActionEvent e) {
168
                doCenterGeometry();
169
            }
170
        });
171
        this.btnCenterError.addActionListener(new ActionListener() {
172
            @Override
173
            public void actionPerformed(ActionEvent e) {
174
                doCenterError();
175
            }
176
        });
177 688 jjdelcerro
        this.btnRefresh.addActionListener(new ActionListener() {
178
            @Override
179
            public void actionPerformed(ActionEvent e) {
180
                doExecutePlan();
181
            }
182
        });
183
        this.tblErrors.getSelectionModel().addListSelectionListener(new ListSelectionListener() {
184
            @Override
185
            public void valueChanged(ListSelectionEvent e) {
186
                doRowSelected();
187
            }
188
        });
189 723 jjdelcerro
        this.tblErrors.addMouseListener(new MouseAdapter() {
190
            @Override
191
            public void mouseClicked(MouseEvent e) {
192 760 jjdelcerro
                if (e.getButton() == MouseEvent.BUTTON1 && e.getClickCount() == 2) {
193 727 jjdelcerro
                    doCenterError();
194 723 jjdelcerro
                }
195
            }
196
        });
197 760 jjdelcerro
198 688 jjdelcerro
        this.btnActions.addActionListener(new ActionListener() {
199
            @Override
200
            public void actionPerformed(ActionEvent e) {
201
                doSelectAction();
202
            }
203
        });
204
        this.btnParametersCancel.addActionListener(new ActionListener() {
205
            @Override
206
            public void actionPerformed(ActionEvent e) {
207
                tabData.setEnabledAt(0, true);
208
                tabData.setEnabledAt(1, false);
209
                tabData.setSelectedIndex(0);
210
                pnlParameters.removeAll();
211
            }
212
        });
213
        this.btnShowErrors.addActionListener(new ActionListener() {
214
            @Override
215
            public void actionPerformed(ActionEvent e) {
216
                doUpdateFilter();
217
            }
218
        });
219
        this.btnShowExceptions.addActionListener(new ActionListener() {
220
            @Override
221
            public void actionPerformed(ActionEvent e) {
222
                doUpdateFilter();
223
            }
224
        });
225
        this.btnVisibleExtentOnly.addActionListener(new ActionListener() {
226
            @Override
227
            public void actionPerformed(ActionEvent e) {
228
                doUpdateFilter();
229
            }
230
        });
231 727 jjdelcerro
        this.btnShowForm.addActionListener(new ActionListener() {
232
            @Override
233
            public void actionPerformed(ActionEvent e) {
234
                services.setShowFormWhenEdit(btnShowForm.isSelected());
235
            }
236
        });
237
        this.btnEraseErrorMarks.addActionListener(new ActionListener() {
238
            @Override
239
            public void actionPerformed(ActionEvent e) {
240
                services.addError(null);
241
            }
242
        });
243 688 jjdelcerro
        DefaultComboBoxModel<ListElement<TopologyRuleFactory>> modelRules = new DefaultComboBoxModel<>();
244 760 jjdelcerro
        modelRules.addElement(new ListElement<>(i18n.getTranslation("_Any_rule"), (TopologyRuleFactory) null));
245 688 jjdelcerro
        List<TopologyRuleFactory> factories = TopologyLocator.getTopologyManager().getRuleFactories();
246
        for (TopologyRuleFactory factory : factories) {
247
            modelRules.addElement(new ListElement<>(factory.getName(), factory));
248
        }
249
        this.cboRules.setModel(modelRules);
250
        this.cboRules.addActionListener(new ActionListener() {
251
            @Override
252
            public void actionPerformed(ActionEvent e) {
253
                // Llama al invokeLater para poder debugguear
254
                SwingUtilities.invokeLater(new Runnable() {
255
                    @Override
256
                    public void run() {
257
                        doUpdateFilter();
258
                    }
259
                });
260
            }
261
        });
262
        this.taskStatusController = ToolsSwingLocator.getTaskStatusSwingManager().createTaskStatusController(
263
                null,
264
                this.lblTaskStatusTitle,
265
                this.lblTaskStatusMessage,
266
                this.pbTaskStatusProgress,
267
                this.btnTaskStatusCancel,
268
                null
269
        );
270
        this.translate();
271
        this.setPreferredSize(new Dimension(700, 200));
272
273
        this.btnShowErrors.setSelected(false);
274
        this.btnShowExceptions.setSelected(false);
275
        this.btnVisibleExtentOnly.setSelected(false);
276 760 jjdelcerro
277 688 jjdelcerro
        this.tabData.setEnabledAt(1, false);
278
279
    }
280 760 jjdelcerro
281 727 jjdelcerro
    @Override
282
    public ImageIcon loadImage(String imageName) {
283
        String name = FilenameUtils.getBaseName(imageName);
284
        IconTheme theme = ToolsSwingLocator.getIconThemeManager().getDefault();
285
        if (theme.exists(name)) {
286
            return theme.get(name);
287
        }
288 760 jjdelcerro
        URL url = this.getClass().getResource("/" + imageName);
289 727 jjdelcerro
        if (url == null) {
290
            return null;
291
        }
292
        return new ImageIcon(url);
293
    }
294 688 jjdelcerro
295
    private void translate() {
296
        ToolsSwingManager tsm = ToolsSwingLocator.getToolsSwingManager();
297
        tsm.translate(this.btnActions);
298 727 jjdelcerro
        tsm.translate(this.btnCenterError);
299
        tsm.translate(this.btnCenterGeometry);
300 688 jjdelcerro
        tsm.translate(this.btnRefresh);
301
        tsm.translate(this.btnShowErrors);
302
        tsm.translate(this.btnShowExceptions);
303 727 jjdelcerro
        tsm.translate(this.btnZoomError);
304
        tsm.translate(this.btnZoomGeometry);
305
        tsm.translate(this.btnEraseErrorMarks);
306 688 jjdelcerro
        tsm.translate(this.btnVisibleExtentOnly);
307
        tsm.translate(this.btnParametersAccept);
308
        tsm.translate(this.btnParametersCancel);
309 727 jjdelcerro
        tsm.translate(this.btnShowForm);
310 688 jjdelcerro
        tsm.translate(this.lblShow);
311
        tsm.translate(this.tabData);
312
    }
313
314
    @Override
315
    public void put(TopologyPlan plan) {
316
        this.plan = plan;
317
        this.taskStatusController.bind(this.plan.getTaskStatus());
318
        this.plan.getTaskStatus().addObserver(new Observer() {
319
            @Override
320
            public void update(Observable o, Object o1) {
321
                doTaskStatusUpdated(o, o1);
322
            }
323
        });
324
        this.linesModel.setReport(plan.getReport());
325
    }
326
327
    @Override
328
    public JComponent asJComponent() {
329
        return this;
330
    }
331
332
    private void doUpdateFilter() {
333
        this.linesModel.setFilter(this.getFilter());
334
    }
335
336
    private String getFilter() {
337
        ExpressionBuilder builder = ExpressionEvaluatorLocator.getManager().createExpressionBuilder();
338
        TopologyRuleFactory ruleFactory = (TopologyRuleFactory) ListElement.getSelected(cboRules);
339 760 jjdelcerro
        if (ruleFactory != null) {
340 688 jjdelcerro
            builder.setValue(
341 760 jjdelcerro
                    builder.eq(
342
                            builder.column(TopologyReport.RULE_ID),
343
                            builder.constant(ruleFactory.getId())
344
                    )
345 688 jjdelcerro
            );
346
        }
347 760 jjdelcerro
        if (this.btnShowErrors.isSelected()) {
348
            if (btnShowExceptions.isSelected()) {
349 688 jjdelcerro
                builder.and(
350
                        builder.or(
351 760 jjdelcerro
                                builder.column(TopologyReport.IS_ERROR),
352
                                builder.column(TopologyReport.IS_EXCEPTION)
353 688 jjdelcerro
                        )
354
                );
355
            } else {
356
                builder.and(
357 760 jjdelcerro
                        builder.column(TopologyReport.IS_ERROR)
358 688 jjdelcerro
                );
359
            }
360 760 jjdelcerro
        } else if (btnShowExceptions.isSelected()) {
361 688 jjdelcerro
            builder.and(
362 760 jjdelcerro
                    builder.column(TopologyReport.IS_EXCEPTION)
363 688 jjdelcerro
            );
364
        }
365 760 jjdelcerro
        if (this.btnVisibleExtentOnly.isSelected()) {
366 688 jjdelcerro
            Envelope workingArea = this.services.getWorkingArea();
367 760 jjdelcerro
            if (workingArea != null) {
368 688 jjdelcerro
                builder.and(
369
                        builder.ST_Intersects(
370 760 jjdelcerro
                                builder.column(TopologyReport.GEOMETRY),
371 688 jjdelcerro
                                builder.geometry(workingArea.getGeometry())
372
                        )
373
                );
374
            }
375
            this.services.addWorkingAreaChangedListener(this.workingAreaChangedListener);
376
        } else {
377
            this.services.removeWorkingAreaChangedListener(this.workingAreaChangedListener);
378
        }
379 760 jjdelcerro
        if (builder.getValue() == null) {
380 688 jjdelcerro
            return null;
381
        }
382
        return builder.toString();
383
    }
384 760 jjdelcerro
385 688 jjdelcerro
    private void doExecutePlan() {
386
        Thread th = new Thread(new Runnable() {
387
            @Override
388
            public void run() {
389
                plan.execute();
390
            }
391
        }, "TopologyPlan-" + plan.getName());
392
        th.start();
393
    }
394
395
    private void doTaskStatusUpdated(final Observable observable, final Object notification) {
396
        if (observable != null && !(observable instanceof TaskStatus)) {
397
            return;
398
        }
399
        if (!SwingUtilities.isEventDispatchThread()) {
400
            SwingUtilities.invokeLater(new Runnable() {
401
                public void run() {
402
                    doTaskStatusUpdated(observable, notification);
403
                }
404
            });
405
            return;
406
        }
407
        TaskStatus taskStatus = (TaskStatus) observable;
408 760 jjdelcerro
        if (taskStatus == null || !taskStatus.isRunning()) {
409 722 jjdelcerro
            this.lblTaskStatusTitle.setVisible(false);
410 688 jjdelcerro
            this.lblTaskStatusMessage.setVisible(false);
411
            this.pbTaskStatusProgress.setVisible(false);
412
            this.btnTaskStatusCancel.setVisible(false);
413
            this.btnRefresh.setEnabled(true);
414 722 jjdelcerro
            I18nManager i18n = ToolsLocator.getI18nManager();
415 760 jjdelcerro
            message(i18n.getTranslation("_Errors") + ": " + this.linesModel.getRowCount());
416 688 jjdelcerro
            return;
417
        }
418
        if (!this.pbTaskStatusProgress.isVisible()) {
419 722 jjdelcerro
            this.lblTaskStatusTitle.setVisible(true);
420 688 jjdelcerro
            this.lblTaskStatusMessage.setVisible(true);
421
            this.pbTaskStatusProgress.setVisible(true);
422
            this.btnTaskStatusCancel.setVisible(true);
423
            this.btnRefresh.setEnabled(false);
424
        }
425
    }
426
427 722 jjdelcerro
    private void message(String msg) {
428
        this.lblTaskStatusTitle.setText(msg);
429
        this.lblTaskStatusTitle.setVisible(true);
430
    }
431 760 jjdelcerro
432 688 jjdelcerro
    private void doSelectAction() {
433
        int n = this.tblErrors.getSelectedRow();
434
        if (n < 0) {
435
            return;
436
        }
437 727 jjdelcerro
        int[] selectedRows = this.tblErrors.getSelectedRows();
438
        TopologyRule rule = this.linesModel.getLine(selectedRows[0]).getRule();
439 688 jjdelcerro
        List<TopologyRuleAction> actions = rule.getActions();
440
        if (actions == null || actions.isEmpty()) {
441
            return;
442 760 jjdelcerro
        }
443
        List<TopologyReportLine> lines = new ArrayList<>();
444 727 jjdelcerro
        for (int selectedRow : selectedRows) {
445
            TopologyReportLine line = this.linesModel.getLine(selectedRow);
446 760 jjdelcerro
            if (line.getRule() == rule) {
447 727 jjdelcerro
                lines.add(line);
448
            }
449 688 jjdelcerro
        }
450
        JPopupMenu menu = new JPopupMenu();
451
        for (TopologyRuleAction action : actions) {
452 722 jjdelcerro
            JMenuItem item;
453 760 jjdelcerro
            if (action.hasParameters()) {
454
                item = new JMenuItem(action.getName() + "...");
455 722 jjdelcerro
            } else {
456 760 jjdelcerro
                item = new JMenuItem(action.getName());
457 722 jjdelcerro
            }
458 727 jjdelcerro
            item.addActionListener(new TopologyRuleActionListener(rule, lines, action));
459 760 jjdelcerro
            if (lines.size() > 1 && action.hasParameters()) {
460 727 jjdelcerro
                item.setEnabled(false);
461
            }
462 688 jjdelcerro
            menu.add(item);
463
        }
464
        menu.show(this.btnActions, 0, this.btnActions.getHeight());
465
    }
466
467
    private void doExecuteRuleAction(
468
            TopologyRule rule,
469 727 jjdelcerro
            List<TopologyReportLine> lines,
470 688 jjdelcerro
            TopologyRuleAction action,
471
            JDynForm form
472
    ) {
473 722 jjdelcerro
        DynObject parameters = null;
474 760 jjdelcerro
        if (form != null) {
475 722 jjdelcerro
            parameters = action.createParameters();
476 760 jjdelcerro
            if (parameters != null) {
477 722 jjdelcerro
                form.getValues(parameters);
478
            }
479
        }
480 727 jjdelcerro
        for (TopologyReportLine line : lines) {
481
            action.execute(rule, line, parameters);
482
        }
483 726 jjdelcerro
        this.tabData.setEnabledAt(0, true);
484
        this.tabData.setEnabledAt(1, false);
485
        this.tabData.setSelectedIndex(0);
486
        this.pnlParameters.removeAll();
487 727 jjdelcerro
        this.services.addError(null);
488 688 jjdelcerro
    }
489
490
    private void doShowActionParametersPanel(
491
            TopologyRule rule,
492 727 jjdelcerro
            List<TopologyReportLine> lines,
493 688 jjdelcerro
            TopologyRuleAction action
494
    ) {
495
        I18nManager i18n = ToolsLocator.getI18nManager();
496
        this.tabData.setEnabledAt(0, false);
497
        this.tabData.setEnabledAt(1, true);
498
        this.tabData.setSelectedIndex(1);
499
500
        try {
501
            JDynForm form = null;
502
            this.lblActionTitle.setText(
503 760 jjdelcerro
                    "<html>"
504
                    + i18n.getTranslation("_Rule") + ": <b>"
505
                    + rule.getName() + "</b>, "
506
                    + i18n.getTranslation("_Action") + ": <b>"
507
                    + action.getName() + "</b></html>"
508 688 jjdelcerro
            );
509 760 jjdelcerro
            this.lblActionDescription.setText("<html>" + action.getShortDescription() + "</html>");
510 722 jjdelcerro
            DynObject parameters = action.createParameters();
511 760 jjdelcerro
            if (parameters != null) {
512 722 jjdelcerro
                form = DynFormLocator.getDynFormManager().createJDynForm(parameters);
513 760 jjdelcerro
                if (form != null) {
514 722 jjdelcerro
                    this.pnlParameters.setLayout(new BorderLayout());
515
                    this.pnlParameters.removeAll();
516
                    this.pnlParameters.add(form.asJComponent(), BorderLayout.CENTER);
517
                    this.pnlParameters.revalidate();
518
                    this.pnlParameters.repaint();
519
                }
520
            }
521 688 jjdelcerro
            this.btnParametersAccept.addActionListener(
522 760 jjdelcerro
                    new TopologyRuleActionParametersListener(rule, lines, action, form)
523 688 jjdelcerro
            );
524
        } catch (Exception ex) {
525 760 jjdelcerro
            LOGGER.warn("Can't show action parameters panel.", ex);
526 688 jjdelcerro
        }
527
    }
528
529 727 jjdelcerro
    private void doZoomGeometry() {
530 688 jjdelcerro
        int n = this.tblErrors.getSelectedRow();
531
        if (n < 0) {
532
            return;
533
        }
534
        TopologyReportLine line = this.linesModel.getLine(n);
535
        Geometry geom = line.getGeometry();
536
        this.services.zoomTo(geom.getEnvelope());
537
    }
538
539 727 jjdelcerro
    private void doZoomError() {
540
        int n = this.tblErrors.getSelectedRow();
541
        if (n < 0) {
542
            return;
543
        }
544
        TopologyReportLine line = this.linesModel.getLine(n);
545
        Geometry geom = line.getError();
546 760 jjdelcerro
        if (geom == null) {
547 727 jjdelcerro
            geom = line.getGeometry();
548
            services.addError(null);
549
        } else {
550
            services.addError(geom);
551
        }
552
        this.services.zoomTo(geom.getEnvelope());
553
    }
554
555
    private void doCenterGeometry() {
556 688 jjdelcerro
        try {
557
            int n = this.tblErrors.getSelectedRow();
558
            if (n < 0) {
559
                return;
560
            }
561
            TopologyReportLine line = this.linesModel.getLine(n);
562
            Geometry geom = line.getGeometry();
563
            this.services.centerTo(geom.centroid());
564
        } catch (Exception ex) {
565
            LOGGER.warn("Can't center topology error", ex);
566
        }
567
    }
568
569 727 jjdelcerro
    private void doCenterError() {
570
        try {
571
            int n = this.tblErrors.getSelectedRow();
572
            if (n < 0) {
573
                return;
574
            }
575
            TopologyReportLine line = this.linesModel.getLine(n);
576
            Geometry geom = line.getError();
577 760 jjdelcerro
            if (geom == null) {
578 727 jjdelcerro
                geom = line.getGeometry();
579
                services.addError(null);
580
            } else {
581
                services.addError(geom);
582
            }
583
            this.services.centerTo(geom.centroid());
584
        } catch (Exception ex) {
585
            LOGGER.warn("Can't center topology error", ex);
586
        }
587
    }
588
589 688 jjdelcerro
    private void doRowSelected() {
590
        try {
591
            int n = this.tblErrors.getSelectedRow();
592
            if (n < 0) {
593
                return;
594
            }
595
            TopologyReportLine line = this.linesModel.getLine(n);
596
            if (line.getFeature1() == null) {
597
                return;
598
            }
599 727 jjdelcerro
            this.services.addError(null);
600
            FeatureSelection selection = line.getDataSet1().getFeatureStore().getFeatureSelection();
601 688 jjdelcerro
            selection.deselectAll();
602
            selection.select(line.getFeature1());
603
        } catch (Exception ex) {
604
            LOGGER.warn("Can't select topology error", ex);
605
        }
606
    }
607
608 760 jjdelcerro
    private class ReportTable implements TableModel {
609 688 jjdelcerro
610
        private TopologyReport report;
611
        private TopologyReportLineSet lines;
612
        private final String[] columnNames;
613
        private final Class[] columnClasses;
614
        private final Set<TableModelListener> tableListeners;
615
        private final ChangeListener reportListener;
616
        private String lastFilter;
617
618
        public ReportTable() {
619
            I18nManager i18n = ToolsLocator.getI18nManager();
620
            this.report = null;
621
            this.lines = null;
622
            this.tableListeners = new HashSet<>();
623
            this.columnNames = new String[]{
624
                i18n.getTranslation("_Rule"),
625
                i18n.getTranslation("_Dataset1"),
626
                i18n.getTranslation("_Dataset2"),
627
                i18n.getTranslation("_Exception"),
628
                i18n.getTranslation("_Description")
629
            };
630
            this.columnClasses = new Class[]{
631
                String.class,
632
                String.class,
633
                String.class,
634
                Boolean.class,
635
                String.class
636
            };
637
            this.reportListener = new ChangeListener() {
638
                @Override
639
                public void stateChanged(final ChangeEvent e) {
640 760 jjdelcerro
                    if (!SwingUtilities.isEventDispatchThread()) {
641 688 jjdelcerro
                        SwingUtilities.invokeLater(new Runnable() {
642
                            @Override
643
                            public void run() {
644
                                stateChanged(e);
645
                            }
646
                        });
647
                        return;
648
                    }
649
                    fireTableChanged();
650
                }
651
            };
652
        }
653
654
        public void setReport(TopologyReport report) {
655
            if (this.report != null) {
656
                this.report.removeChangeListener(this.reportListener);
657
            }
658
            this.report = report;
659
            this.lines = this.report;
660
            this.lines.addChangeListener(this.reportListener);
661
        }
662
663
        public void setFilter(String filter) {
664 760 jjdelcerro
            if (StringUtils.equals(filter, this.lastFilter)) {
665 688 jjdelcerro
                return;
666
            }
667
            this.lines = this.report.getLineSet(filter);
668
            this.lines.addChangeListener(this.reportListener);
669
            this.lastFilter = filter;
670
            this.fireTableChanged();
671
        }
672 760 jjdelcerro
673 688 jjdelcerro
        public TopologyReport getReport() {
674
            return this.report;
675
        }
676
677
        @Override
678
        public int getRowCount() {
679
            if (this.lines == null) {
680
                return 0;
681
            }
682
            return this.lines.size();
683
        }
684
685
        @Override
686
        public int getColumnCount() {
687
            return 5;
688
        }
689
690
        @Override
691
        public String getColumnName(int columnIndex) {
692
            return this.columnNames[columnIndex];
693
        }
694
695
        @Override
696
        public Class<?> getColumnClass(int columnIndex) {
697
            return this.columnClasses[columnIndex];
698
        }
699
700
        @Override
701
        public boolean isCellEditable(int rowIndex, int columnIndex) {
702
            return false;
703
        }
704
705
        @Override
706
        public Object getValueAt(int rowIndex, int columnIndex) {
707
            if (this.lines == null) {
708
                return "";
709
            }
710
            TopologyReportLine line = this.lines.get(rowIndex);
711
            switch (columnIndex) {
712
                case 0:
713
                    return line.getRule().getName();
714
                case 1:
715
                    return line.getDataSet1().getName();
716
                case 2:
717
                    if (line.getDataSet2() == null) {
718
                        return "";
719
                    }
720
                    return line.getDataSet2().getName();
721
                case 3:
722
                    return line.isException();
723
                case 4:
724
                    return line.getDescription();
725
                default:
726
                    return "???";
727
            }
728
        }
729
730
        @Override
731
        public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
732
        }
733
734
        @Override
735
        public void addTableModelListener(TableModelListener l) {
736
            this.tableListeners.add(l);
737
        }
738
739
        @Override
740
        public void removeTableModelListener(TableModelListener l) {
741
            this.tableListeners.remove(l);
742
        }
743
744
        private void fireTableChanged() {
745 760 jjdelcerro
            saveCurrentSelection();
746 688 jjdelcerro
            for (TableModelListener tableListener : this.tableListeners) {
747
                tableListener.tableChanged(new TableModelEvent(this));
748
            }
749 760 jjdelcerro
            restoreCurrentSelection();
750 688 jjdelcerro
        }
751
752
        public TopologyReportLine getLine(int lineNum) {
753
            return this.lines.get(lineNum);
754
        }
755
756
    }
757 760 jjdelcerro
758
    private void saveCurrentSelection() {
759
        this.tblErrors.setSelectionModel(new DefaultListSelectionModel());
760
    }
761
762
    private void restoreCurrentSelection() {
763
        this.tblErrors.setSelectionModel(this.selection);
764
    }
765 688 jjdelcerro
}