OpenConcerto

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

svn://code.openconcerto.org/openconcerto

Rev

Rev 156 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
18 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.
18 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.erp.core.finance.accounting.ui;
15
 
16
import org.openconcerto.erp.config.ComptaPropsConfiguration;
17
import org.openconcerto.erp.core.finance.accounting.action.ImpressionGrandLivreAction;
18
import org.openconcerto.erp.core.finance.accounting.element.MouvementSQLElement;
19
import org.openconcerto.erp.core.finance.accounting.model.ConsultCompteModel;
20
import org.openconcerto.erp.element.objet.ClasseCompte;
21
import org.openconcerto.erp.element.objet.Compte;
22
import org.openconcerto.erp.element.objet.Ecriture;
23
import org.openconcerto.erp.model.LoadingTableListener;
24
import org.openconcerto.erp.rights.ComptaUserRight;
25
import org.openconcerto.sql.Configuration;
26
import org.openconcerto.sql.model.SQLBase;
27
import org.openconcerto.sql.model.SQLSelect;
28 ilm 28
import org.openconcerto.sql.model.SQLSystem;
18 ilm 29
import org.openconcerto.sql.model.SQLTable;
30
import org.openconcerto.sql.model.Where;
144 ilm 31
import org.openconcerto.sql.users.rights.UserRightsManager;
18 ilm 32
import org.openconcerto.ui.DefaultGridBagConstraints;
156 ilm 33
import org.openconcerto.utils.ExceptionHandler;
18 ilm 34
import org.openconcerto.utils.GestionDevise;
35
import org.openconcerto.utils.TableSorter;
36
 
37
import java.awt.Dimension;
38
import java.awt.GridBagConstraints;
39
import java.awt.GridBagLayout;
40
import java.awt.Insets;
41
import java.awt.event.ActionEvent;
42
import java.awt.event.ActionListener;
43
import java.awt.event.MouseAdapter;
44
import java.awt.event.MouseEvent;
45
import java.util.List;
46
 
47
import javax.swing.AbstractAction;
48
import javax.swing.BorderFactory;
49
import javax.swing.JButton;
50
import javax.swing.JFrame;
51
import javax.swing.JLabel;
156 ilm 52
import javax.swing.JOptionPane;
18 ilm 53
import javax.swing.JPanel;
54
import javax.swing.JPopupMenu;
55
import javax.swing.JScrollPane;
56
import javax.swing.JTabbedPane;
57
import javax.swing.JTable;
58
import javax.swing.SwingConstants;
59
import javax.swing.SwingUtilities;
60
import javax.swing.SwingWorker;
61
import javax.swing.event.EventListenerList;
62
 
63
import org.apache.commons.dbutils.handlers.ArrayListHandler;
64
 
65
/***************************************************************************************************
66
 * Panel du grand livre regroupant l'ensemble des ecritures comptables de l'exercice par compte et
67
 * par classe
68
 **************************************************************************************************/
69
public class GrandLivrePanel extends JPanel {
70
 
71
    private JTabbedPane tabbedClasse;
72
    EventListenerList loadingListener = new EventListenerList();
73
 
74
    public GrandLivrePanel() {
75
        this.setLayout(new GridBagLayout());
76
        final GridBagConstraints c = new DefaultGridBagConstraints();
77
        c.weightx = 1;
78
        this.tabbedClasse = new JTabbedPane();
79
 
80
        c.fill = GridBagConstraints.BOTH;
81
        c.weightx = 1;
82
        c.weighty = 1;
83
        c.gridx = 0;
84
 
85
        c.gridy = 0;
86
        c.gridwidth = 2;
87
        this.add(this.tabbedClasse, c);
88
 
89
        JButton buttonImpression = new JButton("Impression");
90
        JButton buttonClose = new JButton("Fermer");
91
        c.gridx = 0;
92
        c.gridy++;
93
        c.weightx = 1;
94
        c.weighty = 0;
95
        c.gridwidth = 1;
96
        c.fill = GridBagConstraints.NONE;
97
        c.anchor = GridBagConstraints.EAST;
98
        this.add(buttonImpression, c);
99
        c.gridx++;
100
        c.weightx = 0;
101
        this.add(buttonClose, c);
102
 
103
        buttonClose.addActionListener(new ActionListener() {
104
            public void actionPerformed(ActionEvent e) {
105
                ((JFrame) SwingUtilities.getRoot(GrandLivrePanel.this)).dispose();
106
            };
107
        });
108
        buttonImpression.addActionListener(new ImpressionGrandLivreAction());
109
    }
110
 
111
    public void loadAsynchronous() {
112
        // On recupere les differentes classes
113
        List<ClasseCompte> liste = ClasseCompte.getClasseCompte();
114
 
156 ilm 115
        if (!liste.isEmpty()) {
18 ilm 116
            for (int k = 0; k < liste.size(); k++) {
117
 
118
                final ClasseCompte ccTmp = liste.get(k);
119
                fireLoading(true);
120
                new SwingWorker<JPanel, Object>() {
121
                    @Override
122
                    protected JPanel doInBackground() throws Exception {
123
                        return initClassePanel(ccTmp);
124
                    }
125
 
126
                    @Override
127
                    protected void done() {
128
                        JPanel initClassePanel;
129
                        try {
130
                            initClassePanel = get();
131
                            initClassePanel.setOpaque(false);
132
                            final JScrollPane scrollPane = new JScrollPane(initClassePanel);
133
                            scrollPane.setOpaque(false);
134
                            scrollPane.setBorder(null);
135
                            scrollPane.getViewport().setOpaque(false);
136
                            // On créer les comptes de chaque classe
137
                            GrandLivrePanel.this.tabbedClasse.addTab(ccTmp.getNom(), scrollPane);
156 ilm 138
                        } catch (Exception e) {
139
                            ExceptionHandler.handle("erreur " + ccTmp.getNom(), e);
18 ilm 140
                        }
141
                        fireLoading(false);
142
                        super.done();
143
                    }
144
                }.execute();
145
 
146
            }
147
        }
148
    }
149
 
150
    /**
151
     * Crée le panel d'un onglet associé à une classe
152
     *
153
     * @param cc ClasseCompte la classe des comptes
154
     * @return JPanel le JPanel associé
155
     */
156
    private JPanel initClassePanel(ClasseCompte cc) {
157
 
158
        final JPanel panelTmp = new JPanel();
159
        long totalDebitClasse = 0;
160
        long totalCreditClasse = 0;
161
 
162
        panelTmp.setLayout(new GridBagLayout());
163
        panelTmp.setOpaque(false);
164
        final GridBagConstraints c = new GridBagConstraints();
165
        c.insets = new Insets(2, 2, 1, 2);
166
        c.fill = GridBagConstraints.HORIZONTAL;
167
        c.anchor = GridBagConstraints.NORTHWEST;
168
        c.gridx = 0;
169
        c.gridy = 0;
170
        c.gridwidth = 1;
171
        c.gridheight = 1;
172
        c.weightx = 1;
173
        c.weighty = 0;
174
 
175
        // Récupération des comptes de la classe avec le total
176
        SQLBase base = ((ComptaPropsConfiguration) Configuration.getInstance()).getSQLBaseSociete();
177
        SQLTable compteTable = base.getTable("COMPTE_PCE");
178
        SQLTable ecritureTable = base.getTable("ECRITURE");
179
 
180
        SQLSelect sel = new SQLSelect(base);
181
        sel.addSelect(compteTable.getKey());
182
        sel.addSelect(compteTable.getField("NUMERO"));
183
        sel.addSelect(compteTable.getField("NOM"));
184
        sel.addSelect(ecritureTable.getField("DEBIT"), "SUM");
185
        sel.addSelect(ecritureTable.getField("CREDIT"), "SUM");
186
 
187
        String function = "REGEXP";
188
        String match = cc.getTypeNumeroCompte();
28 ilm 189
        if (Configuration.getInstance().getBase().getServer().getSQLSystem() == SQLSystem.POSTGRESQL) {
190
            function = "~";
18 ilm 191
        }
192
 
193
        Where w = new Where(compteTable.getField("NUMERO"), function, match);
194
        Where w2 = new Where(ecritureTable.getField("ID_COMPTE_PCE"), "=", compteTable.getKey());
195
 
144 ilm 196
        if (!UserRightsManager.getCurrentUserRights().haveRight(ComptaUserRight.ACCES_NOT_RESCTRICTED_TO_411)) {
18 ilm 197
            // TODO Show Restricted acces in UI
198
            w = w.and(new Where(ecritureTable.getField("COMPTE_NUMERO"), "LIKE", "411%"));
199
        }
200
 
201
        sel.setWhere(w.and(w2));
202
 
203
        String req = sel.asString() + " GROUP BY \"COMPTE_PCE\".\"ID\",\"COMPTE_PCE\".\"NUMERO\",\"COMPTE_PCE\".\"NOM\" ORDER BY \"COMPTE_PCE\".\"NUMERO\"";
204
        System.out.println(req);
205
 
182 ilm 206
        List myList = (List) base.getDataSource().execute(req, new ArrayListHandler());
18 ilm 207
 
208
        JLabel labelTotalClasse = new JLabel();
209
        labelTotalClasse.setOpaque(false);
156 ilm 210
        if (!myList.isEmpty()) {
18 ilm 211
 
212
            /***************************************************************************************
213
             * Création des Panels de chaque compte
214
             **************************************************************************************/
215
            for (int i = 0; i < myList.size(); i++) {
216
 
217
                Object[] objTmp = (Object[]) myList.get(i);
218
 
144 ilm 219
                final Compte compteTmp = new Compte(((Number) objTmp[0]).intValue(), objTmp[1].toString(), objTmp[2].toString(), "", ((Number) objTmp[3]).longValue(),
220
                        ((Number) objTmp[4]).longValue());
18 ilm 221
 
222
                c.fill = GridBagConstraints.HORIZONTAL;
223
                c.weightx = 1;
224
                c.weighty = 0;
225
                c.gridx = 0;
226
                c.gridy++;
227
                panelTmp.add(creerComptePanel(compteTmp), c);
228
 
229
                // calcul du total de la classe
230
                totalDebitClasse += compteTmp.getTotalDebit();
231
                totalCreditClasse += compteTmp.getTotalCredit();
232
            }
233
 
234
            // Total de la classe
235
            labelTotalClasse.setText("Total Classe " + cc.getNom() + " Débit : " + GestionDevise.currencyToString(totalDebitClasse) + " Crédit : " + GestionDevise.currencyToString(totalCreditClasse));
236
 
237
        } else {
238
            labelTotalClasse.setHorizontalAlignment(SwingConstants.CENTER);
239
            labelTotalClasse.setText("Aucune écriture pour la classe " + cc.getNom());
240
        }
241
        c.gridy++;
242
        c.weighty = 1;
243
        panelTmp.add(labelTotalClasse, c);
244
 
245
        return panelTmp;
246
    }
247
 
248
    private JPanel creerComptePanel(final Compte compte) {
249
 
250
        final GridBagConstraints c = new GridBagConstraints();
251
        c.insets = new Insets(2, 2, 1, 2);
252
        c.fill = GridBagConstraints.NONE;
253
        c.anchor = GridBagConstraints.NORTHWEST;
254
        c.gridx = GridBagConstraints.RELATIVE;
255
        c.gridy = 0;
256
        c.gridwidth = 1;
257
        c.gridheight = 1;
258
        c.weightx = 1;
259
        c.weighty = 0;
260
 
261
        // Intitulé du compte
262
        final JPanel panelCompte = new JPanel();
263
        panelCompte.setOpaque(false);
264
        panelCompte.setLayout(new GridBagLayout());
265
        panelCompte.setBorder(BorderFactory.createTitledBorder(compte.getNumero() + " " + compte.getNom()));
266
 
267
        // Bouton Détails +/- du compte
268
        JButton boutonShow = new JButton("+/-");
269
        boutonShow.setOpaque(false);
270
        boutonShow.setHorizontalAlignment(SwingConstants.RIGHT);
271
 
272
        // Total du Compte
273
        JLabel labelCompteDebit = new JLabel("Total Debit : " + GestionDevise.currencyToString(compte.getTotalDebit()));
274
        JLabel labelCompteCredit = new JLabel(" Credit : " + GestionDevise.currencyToString(compte.getTotalCredit()));
275
        labelCompteDebit.setHorizontalAlignment(SwingUtilities.LEFT);
276
        labelCompteCredit.setHorizontalAlignment(SwingUtilities.LEFT);
277
 
278
        JLabel labelTmp = new JLabel(compte.getNumero() + " " + compte.getNom());
279
        labelTmp.setHorizontalAlignment(SwingUtilities.LEFT);
280
 
281
        panelCompte.add(labelTmp, c);
282
        panelCompte.add(labelCompteDebit, c);
283
        panelCompte.add(labelCompteCredit, c);
284
        c.weightx = 1;
285
        c.anchor = GridBagConstraints.NORTHEAST;
286
        panelCompte.add(boutonShow, c);
287
 
288
        boutonShow.addActionListener(new ActionListener() {
289
            private boolean isShow = false;
290
            private JScrollPane scroll = null;
291
 
292
            public void actionPerformed(ActionEvent e) {
293
 
294
                // Afficher la JTable du compte
295
                if (!this.isShow) {
156 ilm 296
 
18 ilm 297
                    JTable tableCpt = createJTableCompte(compte);
156 ilm 298
                    if (tableCpt == null) {
299
                        JOptionPane.showMessageDialog(GrandLivrePanel.this, "Aucune écriture");
300
                        return;
301
                    } else {
302
                        this.scroll = new JScrollPane(tableCpt);
18 ilm 303
 
156 ilm 304
                        // calcul de la taille du JScrollPane
305
                        Dimension d;
306
                        if (tableCpt.getPreferredSize().height > 200) {
307
                            d = new Dimension(this.scroll.getPreferredSize().width, 200);
308
                        } else {
309
                            d = new Dimension(this.scroll.getPreferredSize().width, tableCpt.getPreferredSize().height + 30);
310
                        }
311
                        this.scroll.setPreferredSize(d);
18 ilm 312
 
156 ilm 313
                        c.gridy++;
314
                        c.gridwidth = 4;
315
                        c.weightx = 1;
316
                        c.fill = GridBagConstraints.HORIZONTAL;
317
                        c.anchor = GridBagConstraints.NORTHWEST;
318
                        panelCompte.add(this.scroll, c);
319
 
18 ilm 320
                    }
321
                } else {
156 ilm 322
                    if (this.scroll != null) {
323
                        panelCompte.remove(this.scroll);
324
                    }
18 ilm 325
                    panelCompte.repaint();
326
                    panelCompte.revalidate();
327
                }
328
 
329
                this.isShow = !this.isShow;
330
                SwingUtilities.getRoot(panelCompte).repaint();
331
            }
332
        });
333
 
334
        return panelCompte;
335
    }
336
 
337
    /**
338
     * Cree un JTable contenant les ecritures du compte passé en argument
339
     *
340
     * @param compte
341
     * @return null si aucune ecriture
342
     */
343
    private JTable createJTableCompte(Compte compte) {
344
 
345
        // on cree la JTable
346
        final JTable tableTmp = creerJTable(compte);
347
 
348
        if (tableTmp != null) {
349
 
350
            // On met en place le renderer
351
            EcritureGrandLivreRenderer ecritureRenderer = new EcritureGrandLivreRenderer(((TableSorter) tableTmp.getModel()));
352
 
353
            for (int j = 0; j < tableTmp.getColumnCount(); j++) {
354
                tableTmp.getColumnModel().getColumn(j).setCellRenderer(ecritureRenderer);
355
            }
356
 
357
            // Gestion de la souris sur la JTable
358
            tableTmp.addMouseListener(new MouseAdapter() {
156 ilm 359
                @Override
18 ilm 360
                public void mousePressed(final MouseEvent mE) {
361
 
362
                    if (mE.getButton() == MouseEvent.BUTTON3) {
363
                        JPopupMenu menuDroit = new JPopupMenu();
364
 
365
                        menuDroit.add(new AbstractAction("Voir la source") {
366
 
367
                            public void actionPerformed(ActionEvent e) {
368
                                int row = tableTmp.rowAtPoint(mE.getPoint());
369
 
370
                                TableSorter s = (TableSorter) tableTmp.getModel();
371
 
372
                                int modelIndex = s.modelIndex(row);
373
                                ConsultCompteModel consultCompteModel = ((ConsultCompteModel) s.getTableModel());
374
                                Ecriture ecriture = consultCompteModel.getEcritures().get(modelIndex);
375
 
376
                                MouvementSQLElement.showSource(ecriture.getIdMvt());
377
 
378
                            }
379
                        });
380
                        menuDroit.show(mE.getComponent(), mE.getX(), mE.getY());
381
                    }
382
                }
383
            });
384
 
385
        }
386
        return tableTmp;
387
    }
388
 
389
    private JTable creerJTable(Compte compte) {
390
 
391
        ConsultCompteModel model = new ConsultCompteModel(compte);
392
        TableSorter s = new TableSorter(model);
393
        JTable tableTmp = new JTable(s);
394
        s.setTableHeader(tableTmp.getTableHeader());
395
        if (model.getEcritures() != null) {
396
 
397
            return tableTmp;
398
        } else {
399
            return null;
400
        }
401
    }
402
 
403
    public void addLoadingListener(LoadingTableListener l) {
404
        this.loadingListener.add(LoadingTableListener.class, l);
405
    }
406
 
407
    int nbLoading = 0;
408
 
409
    public void fireLoading(boolean isLoading) {
410
        if (isLoading) {
411
            nbLoading++;
412
        } else {
413
            nbLoading--;
414
        }
415
 
416
        for (LoadingTableListener l : this.loadingListener.getListeners(LoadingTableListener.class)) {
417
            l.isLoading(nbLoading > 0);
418
        }
419
    }
420
}