OpenConcerto

Dépôt officiel du code source de l'ERP OpenConcerto
sonarqube

svn://code.openconcerto.org/openconcerto

Rev

Rev 142 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
17 ilm 1
/*
2
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3
 *
182 ilm 4
 * Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
17 ilm 5
 *
6
 * The contents of this file are subject to the terms of the GNU General Public License Version 3
7
 * only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
8
 * copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
9
 * language governing permissions and limitations under the License.
10
 *
11
 * When distributing the software, include this License Header Notice in each file.
12
 */
13
 
14
 package org.openconcerto.sql.view.list;
15
 
16
import org.openconcerto.sql.Configuration;
17
import org.openconcerto.sql.model.SQLField;
19 ilm 18
import org.openconcerto.sql.model.SQLRow;
83 ilm 19
import org.openconcerto.sql.model.SQLRowAccessor;
93 ilm 20
import org.openconcerto.sql.model.SQLRowValues;
132 ilm 21
import org.openconcerto.sql.model.SQLSelect;
17 ilm 22
import org.openconcerto.sql.model.Where;
23
import org.openconcerto.sql.request.ComboSQLRequest;
83 ilm 24
import org.openconcerto.sql.sqlobject.ITextArticleWithCompletionCellEditor;
17 ilm 25
import org.openconcerto.sql.sqlobject.ITextWithCompletion;
26
import org.openconcerto.sql.sqlobject.SelectionListener;
83 ilm 27
import org.openconcerto.sql.sqlobject.SelectionRowListener;
17 ilm 28
import org.openconcerto.ui.TextAreaRenderer;
132 ilm 29
import org.openconcerto.utils.cc.ITransformer;
17 ilm 30
 
31
import java.beans.PropertyChangeEvent;
32
import java.beans.PropertyChangeListener;
33
import java.sql.Types;
34
import java.util.HashMap;
35
import java.util.Iterator;
67 ilm 36
import java.util.LinkedHashMap;
17 ilm 37
import java.util.List;
38
import java.util.Set;
39
import java.util.Vector;
40
 
41
import javax.swing.SwingUtilities;
42
import javax.swing.event.CellEditorListener;
43
import javax.swing.event.ChangeEvent;
44
import javax.swing.table.TableCellEditor;
45
 
83 ilm 46
public class AutoCompletionManager implements SelectionRowListener, SelectionListener {
17 ilm 47
 
48
    private SQLTableElement fromTableElement;
49
    private RowValuesTable table;
50
    private TextTableCellEditorWithCompletion editor;
51
    private int lastSelectedComboId = 1;
52
    protected boolean optOk, foreign;
53
    protected boolean disableCompletion;
54
 
55
    private SQLField fillFrom;
56
    private RowValuesTableModel tableModel;
57
    ITextWithCompletion t;
41 ilm 58
    SQLTextComboTableCellEditor textComboCellEdit;
17 ilm 59
 
60
    public AutoCompletionManager(SQLTableElement fromTableElement, SQLField fillFrom, RowValuesTable table, RowValuesTableModel tableModel) {
61
        this(fromTableElement, fillFrom, table, tableModel, ITextWithCompletion.MODE_CONTAINS, false);
62
    }
63
 
65 ilm 64
    // FIXME Le validstatechecker est à passer au SQLTableElement
17 ilm 65
    public AutoCompletionManager(SQLTableElement fromTableElement, SQLField fillFrom, RowValuesTable table, RowValuesTableModel tableModel, int modeCompletion, boolean expandWithShowAs,
65 ilm 66
            boolean foreign, ValidStateChecker checker) {
17 ilm 67
 
68
        this.foreign = foreign;
69
        List<String> l = new Vector<String>();
70
 
71
        if (expandWithShowAs) {
72
            List<SQLField> lSQLFields = Configuration.getInstance().getShowAs().getFieldExpand(fillFrom.getTable());
73
            for (int i = 0; i < lSQLFields.size(); i++) {
74
                l.add(lSQLFields.get(i).getName());
75
            }
76
        } else {
77
            l.add(fillFrom.getName());
78
        }
79
        ComboSQLRequest req = new ComboSQLRequest(fillFrom.getTable(), l);
65 ilm 80
        init(fromTableElement, fillFrom, table, tableModel, modeCompletion, req, foreign, checker);
17 ilm 81
 
82
    }
83
 
84
    public AutoCompletionManager(SQLTableElement fromTableElement, SQLField fillFrom, RowValuesTable table, RowValuesTableModel tableModel, int modeCompletion, boolean expandWithShowAs) {
65 ilm 85
        this(fromTableElement, fillFrom, table, tableModel, modeCompletion, expandWithShowAs, false, new ValidStateChecker());
17 ilm 86
    }
87
 
88
    public AutoCompletionManager(SQLTableElement fromTableElement, SQLField fillFrom, RowValuesTable table, RowValuesTableModel tableModel, int modeCompletion, ComboSQLRequest req) {
89
        init(fromTableElement, fillFrom, table, tableModel, modeCompletion, req, false);
90
    }
91
 
92
    public void init(SQLTableElement fromTableElement, SQLField fillFrom, RowValuesTable table, RowValuesTableModel tableModel, int modeCompletion, ComboSQLRequest req, boolean foreign) {
65 ilm 93
        init(fromTableElement, fillFrom, table, tableModel, modeCompletion, req, foreign, new ValidStateChecker());
94
    }
17 ilm 95
 
94 ilm 96
    private ITextArticleWithCompletionCellEditor articleCombo;
97
 
67 ilm 98
    public void init(final SQLTableElement fromTableElement, final SQLField fillFrom, RowValuesTable table, RowValuesTableModel tableModel, int modeCompletion, ComboSQLRequest req, boolean foreign,
65 ilm 99
            ValidStateChecker validStateChecker) {
100
 
17 ilm 101
        this.tableModel = tableModel;
102
        this.fromTableElement = fromTableElement;
103
 
104
        this.fillFrom = fillFrom;
105
 
106
        this.table = table;
107
 
83 ilm 108
        TableCellEditor cellEdit = this.fromTableElement.getTableCellEditor(table);
17 ilm 109
        if (foreign) {
110
            if (cellEdit instanceof SQLTextComboTableCellEditor) {
41 ilm 111
                this.textComboCellEdit = (SQLTextComboTableCellEditor) cellEdit;
17 ilm 112
                textComboCellEdit.addSelectionListener(new PropertyChangeListener() {
113
 
114
                    @Override
115
                    public void propertyChange(PropertyChangeEvent evt) {
116
 
117
                        int i = textComboCellEdit.getComboSelectedId();
118
                        if (AutoCompletionManager.this.lastSelectedComboId != i) {
67 ilm 119
                            if (fromTableElement.getField().getForeignTable().equals(fillFrom.getTable())) {
120
                                idSelected(i, null);
121
                            } else {
122
                                int selectedID = SQLRow.NONEXISTANT_ID;
123
                                final SQLRow selectedRow = textComboCellEdit.getCombo().getSelectedRow();
124
                                if (selectedRow != null) {
125
                                    selectedID = selectedRow.getForeignRow("ID_" + fillFrom.getTable().getName()).getID();
126
                                }
127
                                idSelected(selectedID, null);
128
                            }
17 ilm 129
                        }
130
                        AutoCompletionManager.this.lastSelectedComboId = i;
131
                        System.err.println("editing stopped");
132
                    }
133
                });
134
 
135
                textComboCellEdit.addCellEditorListener(new CellEditorListener() {
136
                    @Override
137
                    public void editingCanceled(ChangeEvent e) {
138
                        AutoCompletionManager.this.lastSelectedComboId = textComboCellEdit.getComboSelectedId();
139
                    }
140
 
141
                    @Override
142
                    public void editingStopped(ChangeEvent e) {
143
                        AutoCompletionManager.this.lastSelectedComboId = textComboCellEdit.getComboSelectedId();
144
                    }
145
                });
146
 
147
            }
83 ilm 148
        } else if (cellEdit instanceof ITextArticleWithCompletionCellEditor) {
94 ilm 149
            this.articleCombo = (ITextArticleWithCompletionCellEditor) cellEdit;
150
            this.articleCombo.addSelectionListener(this);
17 ilm 151
        } else {
152
 
153
            this.t = new ITextWithCompletion(req, true);
154
            this.t.setModeCompletion(modeCompletion);
65 ilm 155
            this.editor = new TextTableCellEditorWithCompletion(table, this.t, validStateChecker);
17 ilm 156
 
157
            if (this.fillFrom.getType().getType() == Types.VARCHAR) {
158
                this.t.setLimitedSize(this.fillFrom.getType().getSize());
159
                this.editor.setLimitedSize(this.fillFrom.getType().getSize());
160
            }
161
 
162
            this.fromTableElement.setEditor(this.editor);
163
            this.fromTableElement.setRenderer(new TextAreaRenderer());
164
 
165
            this.t.addSelectionListener(this);
166
        }
167
    }
168
 
67 ilm 169
    private HashMap<String, String> fillBy = new LinkedHashMap<String, String>();
17 ilm 170
    private int lastId = -1;
171
    private int lastEditingRow = -1;
172
 
173
    public void fill(String string, String string2) {
174
        this.fillBy.put(string, string2);
175
 
176
    }
177
 
83 ilm 178
    public void idSelected(int id, Object source) {
179
 
17 ilm 180
        // Le Text correspond a un id
181
        final int rowE = this.table.getEditingRow();
182
        if (rowE < 0) {
183
            this.lastEditingRow = rowE;
184
            return;
185
        }
186
 
187
        if (this.lastEditingRow == rowE && this.lastId == id) {
188
            // Evite de reremplir si l'on reselectionne le meme id sur la meme ligne
189
            return;
190
        }
191
        if (id > 1) {
83 ilm 192
            this.lastId = id;
193
            this.lastEditingRow = rowE;
17 ilm 194
 
195
            // On arrete l'edition nous meme pour eviter qu'un click externe fasse un cancelEditing
196
            if (this.table.getCellEditor() != null && !this.foreign) {
197
                this.table.getCellEditor().stopCellEditing();
198
            }
132 ilm 199
 
83 ilm 200
            fillWithSelection(null, id, rowE);
201
        }
202
    }
17 ilm 203
 
83 ilm 204
    @Override
205
    public void rowSelected(SQLRowAccessor row, Object source) {
206
        final int rowE = this.table.getEditingRow();
207
        if (rowE < 0 || row == null) {
208
            this.lastEditingRow = rowE;
209
            return;
210
        }
17 ilm 211
 
83 ilm 212
        this.lastEditingRow = rowE;
213
 
214
        // On arrete l'edition nous meme pour eviter qu'un click externe fasse un cancelEditing
215
        if (this.table.getCellEditor() != null && !this.foreign) {
216
            this.table.getCellEditor().stopCellEditing();
217
        }
218
        fillWithSelection(row, SQLRow.NONEXISTANT_ID, rowE);
219
    }
220
 
221
    private void fillWithSelection(final SQLRowAccessor r, final int id, final int rowE) {
93 ilm 222
 
223
        final SQLRowAccessor rowDest = (rowE >= 0 && rowE <= this.table.getRowCount()) ? this.table.getRowValuesTableModel().getRowValuesAt(rowE) : null;
224
 
83 ilm 225
        new Thread(new Runnable() {
226
            public void run() {
227
                // final SQLRowValues rowV = new
228
                // SQLRowValues(AutoCompletionManager.this.fillFrom.getTable());
229
                final SQLRow rowV;
230
                if (r != null) {
182 ilm 231
                    rowV = r.fetchNewRow(false);
83 ilm 232
                } else {
233
                    rowV = AutoCompletionManager.this.fillFrom.getTable().getRow(id);
234
                }
142 ilm 235
                // Test pour éviter de perdre la sélection d'un article ayant la même désignation
236
                // mais un code différent (Problème remonté par Afhymat avec la tabulation)
237
                if (fillFrom != null && fillFrom.getTable().getName().equals("ARTICLE") && fillFrom.getName().equals("NOM") && rowDest != null && !rowDest.isUndefined()) {
238
                    SQLRowAccessor rowArt = rowDest.getForeign("ID_ARTICLE");
239
                    if (rowArt != null && !rowArt.isUndefined() && rowArt.getString("NOM") != null && rowArt.getString("NOM").trim().equalsIgnoreCase(rowV.getString("NOM").trim())) {
240
                        return;
241
                    }
242
                }
243
 
83 ilm 244
                final Set<String> keys = AutoCompletionManager.this.fillBy.keySet();
245
                // Fill the table model rowvalue with the selected item using the fields defined
246
                // with 'fill'
247
 
248
                SwingUtilities.invokeLater(new Runnable() {
249
                    public void run() {
250
                        for (Iterator<String> iter = keys.iterator(); iter.hasNext();) {
251
                            String from = iter.next();
252
                            String to = AutoCompletionManager.this.fillBy.get(from);
93 ilm 253
                            Object fromV = getValueFrom(rowV, from, rowDest);
83 ilm 254
                            int column = AutoCompletionManager.this.tableModel.getColumnForField(to);
255
                            if (column >= 0) {
256
 
257
                                // Request focus
258
                                if (AutoCompletionManager.this.table.getRowValuesTableModel().getValueAt(rowE, column) == null
259
                                        || !AutoCompletionManager.this.table.getRowValuesTableModel().getValueAt(rowE, column).equals(fromV)) {
260
                                    AutoCompletionManager.this.table.getRowValuesTableModel().setValueAt(fromV, rowE, column);
132 ilm 261
                                    // Test Only if not foreign --> Bug avec le
142 ilm 262
                                    // sqltextcombocelleditor, si test edit cellAt -> fire
263
                                    // idSelected
132 ilm 264
                                    // -1 sur la combo ce qui entraine une déselection (Bug Remonté
265
                                    // par SA Poulignier)
266
                                    if (!AutoCompletionManager.this.foreign && AutoCompletionManager.this.table.getEditingColumn() == column
267
                                            && AutoCompletionManager.this.table.getEditingRow() == rowE) {
83 ilm 268
                                        AutoCompletionManager.this.table.editingCanceled(null);
269
                                        AutoCompletionManager.this.table.setColumnSelectionInterval(column, column);
270
                                        AutoCompletionManager.this.table.setRowSelectionInterval(rowE, rowE);
271
                                        if (AutoCompletionManager.this.table.editCellAt(rowE, column)) {
272
                                            if (AutoCompletionManager.this.table.getEditorComponent() != null) {
273
                                                AutoCompletionManager.this.table.getEditorComponent().requestFocusInWindow();
17 ilm 274
                                            }
275
                                        }
276
                                    }
277
                                }
83 ilm 278
                            } else {
279
                                // Not in the table
280
                                AutoCompletionManager.this.table.getRowValuesTableModel().putValue(fromV, rowE, to);
17 ilm 281
                            }
282
                        }
283
 
83 ilm 284
                        AutoCompletionManager.this.table.resizeAndRepaint();
285
                    }
286
                });
287
            }
288
        }).start();
17 ilm 289
    }
290
 
142 ilm 291
    public Set<String> getFieldsFrom() {
292
        return this.fillBy.keySet();
293
    }
294
 
182 ilm 295
    public String getToField(String fromField) {
296
        return this.fillBy.get(fromField);
297
    }
298
 
142 ilm 299
    public void fillRowValues(SQLRowAccessor from, Set<String> fields, SQLRowValues to) {
300
        for (String fromField : fields) {
93 ilm 301
            String toField = AutoCompletionManager.this.fillBy.get(fromField);
302
            to.put(toField, getValueFrom(from.asRow(), fromField, to));
303
        }
304
    }
305
 
306
    protected Object getValueFrom(SQLRow row, String field, SQLRowAccessor rowDest) {
19 ilm 307
        return row.getObject(field);
308
    }
309
 
132 ilm 310
    public void setSelectTransformer(ITransformer<SQLSelect, SQLSelect> selTrans) {
311
        if (this.t != null) {
312
            this.t.setSelectTransformer(selTrans);
313
        } else if (this.textComboCellEdit != null) {
314
            this.textComboCellEdit.setSelectTransformer(selTrans);
315
        } else if (this.articleCombo != null) {
316
            this.articleCombo.setSelectTransformer(selTrans);
317
        }
318
    }
319
 
17 ilm 320
    public void setWhere(Where w) {
41 ilm 321
        if (this.t != null) {
322
            this.t.setWhere(w);
83 ilm 323
        } else if (this.textComboCellEdit != null) {
41 ilm 324
            this.textComboCellEdit.setWhere(w);
94 ilm 325
        } else if (this.articleCombo != null) {
326
            this.articleCombo.setWhere(w);
41 ilm 327
        }
17 ilm 328
    }
329
 
330
    public void setFillWithField(String s) {
331
        this.t.setFillWithField(s);
332
    }
333
}