OpenConcerto

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

svn://code.openconcerto.org/openconcerto

Rev

Rev 156 | Rev 180 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 156 Rev 174
1
/*
1
/*
2
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
2
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3
 * 
3
 * 
4
 * Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
4
 * Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
5
 * 
5
 * 
6
 * The contents of this file are subject to the terms of the GNU General Public License Version 3
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
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
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.
9
 * language governing permissions and limitations under the License.
10
 * 
10
 * 
11
 * When distributing the software, include this License Header Notice in each file.
11
 * When distributing the software, include this License Header Notice in each file.
12
 */
12
 */
13
 
13
 
14
 package org.openconcerto.erp.core.sales.pos.ui;
14
 package org.openconcerto.erp.core.sales.pos.ui;
15
 
15
 
16
import org.openconcerto.erp.core.sales.pos.POSConfiguration;
16
import org.openconcerto.erp.core.sales.pos.POSConfiguration;
17
import org.openconcerto.erp.core.sales.pos.io.BarcodeReader;
17
import org.openconcerto.erp.core.sales.pos.io.BarcodeReader;
18
import org.openconcerto.erp.core.sales.pos.io.ConcertProtocol;
18
import org.openconcerto.erp.core.sales.pos.io.ConcertProtocol;
19
import org.openconcerto.erp.core.sales.pos.io.ESCSerialDisplay;
19
import org.openconcerto.erp.core.sales.pos.io.ESCSerialDisplay;
20
import org.openconcerto.erp.core.sales.pos.io.TicketPrinter;
20
import org.openconcerto.erp.core.sales.pos.io.TicketPrinter;
21
import org.openconcerto.erp.core.sales.pos.model.Article;
21
import org.openconcerto.erp.core.sales.pos.model.Article;
22
import org.openconcerto.erp.core.sales.pos.model.Client;
22
import org.openconcerto.erp.core.sales.pos.model.Client;
23
import org.openconcerto.erp.core.sales.pos.model.Paiement;
23
import org.openconcerto.erp.core.sales.pos.model.Paiement;
24
import org.openconcerto.erp.core.sales.pos.model.ReceiptCode;
24
import org.openconcerto.erp.core.sales.pos.model.ReceiptCode;
25
import org.openconcerto.erp.core.sales.pos.model.RegisterFiles;
25
import org.openconcerto.erp.core.sales.pos.model.RegisterFiles;
26
import org.openconcerto.erp.core.sales.pos.model.RegisterLog;
26
import org.openconcerto.erp.core.sales.pos.model.RegisterLog;
27
import org.openconcerto.erp.core.sales.pos.model.RegisterLogEntry.ReceiptEntry;
27
import org.openconcerto.erp.core.sales.pos.model.RegisterLogEntry.ReceiptEntry;
28
import org.openconcerto.erp.core.sales.pos.model.RegisterState.Status;
28
import org.openconcerto.erp.core.sales.pos.model.RegisterState.Status;
29
import org.openconcerto.erp.core.sales.pos.model.Ticket;
29
import org.openconcerto.erp.core.sales.pos.model.Ticket;
-
 
30
import org.openconcerto.erp.core.sales.pos.model.TicketItem;
30
import org.openconcerto.erp.preferences.TemplateNXProps;
31
import org.openconcerto.erp.preferences.TemplateNXProps;
31
import org.openconcerto.sql.element.SQLElementDirectory;
32
import org.openconcerto.sql.element.SQLElementDirectory;
32
import org.openconcerto.utils.FileUtils;
33
import org.openconcerto.utils.FileUtils;
33
import org.openconcerto.utils.Pair;
-
 
34
import org.openconcerto.utils.StringUtils;
34
import org.openconcerto.utils.StringUtils;
35
 
35
 
36
import java.awt.event.KeyEvent;
36
import java.awt.event.KeyEvent;
37
import java.io.File;
37
import java.io.File;
38
import java.io.FileOutputStream;
38
import java.io.FileOutputStream;
39
import java.io.IOException;
39
import java.io.IOException;
40
import java.math.BigDecimal;
40
import java.math.BigDecimal;
41
import java.math.RoundingMode;
41
import java.math.RoundingMode;
42
import java.sql.SQLException;
42
import java.sql.SQLException;
43
import java.text.ParseException;
43
import java.text.ParseException;
44
import java.util.ArrayList;
44
import java.util.ArrayList;
45
import java.util.Calendar;
45
import java.util.Calendar;
46
import java.util.HashSet;
46
import java.util.HashSet;
47
import java.util.List;
47
import java.util.List;
48
import java.util.Set;
48
import java.util.Set;
49
import java.util.Timer;
49
import java.util.Timer;
50
import java.util.TimerTask;
50
import java.util.TimerTask;
51
 
51
 
52
import javax.swing.JOptionPane;
52
import javax.swing.JOptionPane;
53
 
53
 
54
import org.jdom2.JDOMException;
54
import org.jdom2.JDOMException;
55
 
55
 
56
public class CaisseControler implements BarcodeListener {
56
public class CaisseControler implements BarcodeListener {
57
 
57
 
58
    private Article articleSelected;
58
    private Article articleSelected;
59
    private Paiement paiementSelected;
59
    private Paiement paiementSelected;
60
    private Ticket t;
60
    private Ticket t;
61
    private Client client = Client.NONE;
61
    private Client client = Client.NONE;
62
    private List<CaisseListener> listeners = new ArrayList<CaisseListener>();
62
    private List<CaisseListener> listeners = new ArrayList<>();
63
 
63
 
64
    private final BarcodeReader r;
64
    private final BarcodeReader r;
65
    private Paiement p1 = new Paiement(Paiement.ESPECES);
65
    private Paiement p1 = new Paiement(Paiement.ESPECES);
66
    private Paiement p2 = new Paiement(Paiement.CB);
66
    private Paiement p2 = new Paiement(Paiement.CB);
67
    private Paiement p3 = new Paiement(Paiement.CHEQUE);
67
    private Paiement p3 = new Paiement(Paiement.CHEQUE);
68
    private final CaisseFrame caisseFrame;
68
    private final CaisseFrame caisseFrame;
69
    private final POSDisplay lcd;
69
    private final POSDisplay lcd;
-
 
70
    private TicketItem ticketItemSelected;
70
 
71
 
71
    public CaisseControler(CaisseFrame caisseFrame) throws ParseException, JDOMException, IOException {
72
    public CaisseControler(CaisseFrame caisseFrame) throws ParseException, JDOMException, IOException {
72
        this.caisseFrame = caisseFrame;
73
        this.caisseFrame = caisseFrame;
73
        final RegisterLog lastLog = caisseFrame.getFiles().getLastLog();
74
        final RegisterLog lastLog = caisseFrame.getFiles().getLastLog();
74
        if (lastLog == null || lastLog.getRegisterState().getStatus() != Status.OPEN)
75
        if (lastLog == null || lastLog.getRegisterState().getStatus() != Status.OPEN)
75
            throw new IllegalStateException("Not open");
76
            throw new IllegalStateException("Not open");
76
        final String lastHash = lastLog.getLastReceiptHash();
77
        final String lastHash = lastLog.getLastReceiptHash();
77
 
78
 
78
        final ReceiptEntry lastReceiptEvent = lastLog.getLastReceiptCreationEvent();
79
        final ReceiptEntry lastReceiptEvent = lastLog.getLastReceiptCreationEvent();
79
        final int dayIndex;
80
        final int dayIndex;
80
        if (lastReceiptEvent == null) {
81
        if (lastReceiptEvent == null) {
81
            dayIndex = 1;
82
            dayIndex = 1;
82
        } else {
83
        } else {
83
            final ReceiptCode lastCode = lastReceiptEvent.getCode();
84
            final ReceiptCode lastCode = lastReceiptEvent.getCode();
84
            dayIndex = lastCode.getDayIndex() + 1;
85
            dayIndex = lastCode.getDayIndex() + 1;
85
        }
86
        }
86
        final POSConfiguration posConf = getPOSConf();
87
        final POSConfiguration posConf = getPOSConf();
87
        this.t = new Ticket(posConf.getPosID(), dayIndex, lastHash);
88
        this.t = new Ticket(posConf.getPosID(), dayIndex, lastHash);
88
 
89
 
89
        this.t.addPaiement(this.p1);
90
        this.t.addPaiement(this.p1);
90
        this.t.addPaiement(this.p2);
91
        this.t.addPaiement(this.p2);
91
        this.t.addPaiement(this.p3);
92
        this.t.addPaiement(this.p3);
92
 
93
 
93
        final int scanDelay = posConf.getScanDelay();
94
        final int scanDelay = posConf.getScanDelay();
94
        this.r = new BarcodeReader(scanDelay);
95
        this.r = new BarcodeReader(scanDelay);
95
        this.r.start();
96
        this.r.start();
96
        this.r.addBarcodeListener(this);
97
        this.r.addBarcodeListener(this);
97
        if (posConf.getLCDType().equals("serial")) {
98
        if (posConf.getLCDType().equals("serial")) {
98
            lcd = new ESCSerialDisplay(posConf.getLCDPort());
99
            this.lcd = new ESCSerialDisplay(posConf.getLCDPort());
99
        } else {
100
        } else {
100
            lcd = new PrinterPOSDisplay(posConf.getLCDPort());
101
            this.lcd = new PrinterPOSDisplay(posConf.getLCDPort());
101
        }
102
        }
102
        this.setLCDDefaultDisplay(0);
103
        this.setLCDDefaultDisplay(0);
103
    }
104
    }
104
 
105
 
105
    public final CaisseFrame getCaisseFrame() {
106
    public final CaisseFrame getCaisseFrame() {
106
        return this.caisseFrame;
107
        return this.caisseFrame;
107
    }
108
    }
108
 
109
 
109
    protected final POSConfiguration getPOSConf() {
110
    protected final POSConfiguration getPOSConf() {
110
        return getCaisseFrame().getPOSConf();
111
        return getCaisseFrame().getPOSConf();
111
    }
112
    }
112
 
113
 
113
    public Article getArticleSelected() {
114
    public Article getArticleSelected() {
114
        return this.articleSelected;
115
        return this.articleSelected;
115
    }
116
    }
116
 
117
 
117
    public Paiement getPaiementSelected() {
118
    public Paiement getPaiementSelected() {
118
        return this.paiementSelected;
119
        return this.paiementSelected;
119
    }
120
    }
120
 
121
 
121
    void setArticleSelected(Article a) {
122
    void setArticleSelected(Article a) {
122
        if (a != articleSelected) {
123
        if (a != this.articleSelected) {
123
            this.articleSelected = a;
124
            this.articleSelected = a;
124
            this.paiementSelected = null;
125
            this.paiementSelected = null;
125
            fire();
126
            fire();
126
        }
127
        }
127
    }
128
    }
128
 
129
 
129
    void setPaiementSelected(Paiement p) {
130
    void setPaiementSelected(Paiement p) {
130
        this.paiementSelected = p;
131
        this.paiementSelected = p;
131
        this.articleSelected = null;
132
        this.articleSelected = null;
-
 
133
        this.ticketItemSelected = null;
132
        fire();
134
        fire();
133
    }
135
    }
134
 
136
 
135
    // Listeners
137
    // Listeners
136
    private void fire() {
138
    private void fire() {
137
        int stop = this.listeners.size();
139
        int stop = this.listeners.size();
138
        for (int i = 0; i < stop; i++) {
140
        for (int i = 0; i < stop; i++) {
139
            this.listeners.get(i).caisseStateChanged();
141
            this.listeners.get(i).caisseStateChanged();
140
        }
142
        }
141
    }
143
    }
142
 
144
 
143
    void addCaisseListener(CaisseListener l) {
145
    void addCaisseListener(CaisseListener l) {
144
        this.listeners.add(l);
146
        this.listeners.add(l);
145
    }
147
    }
146
 
148
 
147
    // Customer
149
    // Customer
148
    public void setClient(Client client) {
150
    public void setClient(Client client) {
149
        if (client == null) {
151
        if (client == null) {
150
            throw new IllegalArgumentException("Customer cannot be null");
152
            throw new IllegalArgumentException("Customer cannot be null");
151
        }
153
        }
152
        this.client = client;
154
        this.client = client;
153
        this.t.setClient(client);
155
        this.t.setClient(client);
154
        fire();
156
        fire();
155
    }
157
    }
156
 
158
 
157
    public boolean isClientDefined() {
159
    public boolean isClientDefined() {
158
        return this.client != Client.NONE;
160
        return this.client != Client.NONE;
159
    }
161
    }
160
 
162
 
161
    public Client getClient() {
163
    public Client getClient() {
162
        return client;
164
        return this.client;
-
 
165
    }
-
 
166
 
-
 
167
    public void setCodePostal(String codePostal) {
-
 
168
        this.t.setCodePostal(codePostal);
163
    }
169
    }
164
 
170
 
165
    // Articles
171
    // Articles
166
    public void addArticle(Article a) {
172
    public void addArticle(Article a) {
167
        this.t.addArticle(a);
173
        this.t.addArticle(a);
168
        fire();
174
        fire();
169
        String price = TicketCellRenderer.centsToString(a.getPriceWithTax().movePointRight(2).setScale(0, RoundingMode.HALF_UP).intValue());
175
        String price = TicketCellRenderer.centsToString(a.getPriceWithTax().movePointRight(2).setScale(0, RoundingMode.HALF_UP).intValue());
170
        this.setLCD(a.getName(), price, 0);
176
        this.setLCD(a.getName(), price, 0);
171
        this.setLCDDefaultDisplay(2);
177
        this.setLCDDefaultDisplay(2);
172
    }
178
    }
173
 
179
 
174
    void incrementArticle(Article a) {
180
    void incrementArticle(Article a) {
175
        this.t.incrementArticle(a);
181
        this.t.incrementArticle(a);
176
        fire();
182
        fire();
177
        String price = TicketCellRenderer.centsToString(a.getPriceWithTax().movePointRight(2).setScale(0, RoundingMode.HALF_UP).intValue());
183
        String price = TicketCellRenderer.centsToString(a.getPriceWithTax().movePointRight(2).setScale(0, RoundingMode.HALF_UP).intValue());
178
        this.setLCD(a.getName(), price, 0);
184
        this.setLCD(a.getName(), price, 0);
179
        this.setLCDDefaultDisplay(2);
185
        this.setLCDDefaultDisplay(2);
180
    }
186
    }
181
 
187
 
182
    void removeArticle(Article a) {
188
    void removeArticle(Article a) {
183
        this.t.removeArticle(a);
189
        this.t.removeArticle(a);
184
        fire();
190
        fire();
185
    }
191
    }
186
 
192
 
187
    // Paiements
193
    // Paiements
188
    public List<Paiement> getPaiements() {
194
    public List<Paiement> getPaiements() {
189
        return this.t.getPaiements();
195
        return this.t.getPaiements();
190
    }
196
    }
191
 
197
 
192
    public void addPaiement(Paiement p) {
198
    public void addPaiement(Paiement p) {
193
        this.t.addPaiement(p);
199
        this.t.addPaiement(p);
194
        fire();
200
        fire();
195
    }
201
    }
196
 
202
 
197
    public void clearPaiement(Paiement paiement) {
203
    public void clearPaiement(Paiement paiement) {
198
        if (this.p1.equals(paiement) || this.p2.equals(paiement) || this.p3.equals(paiement)) {
204
        if (this.p1.equals(paiement) || this.p2.equals(paiement) || this.p3.equals(paiement)) {
199
            paiement.setMontantInCents(0);
205
            paiement.setMontantInCents(0);
200
        }
206
        }
201
        fire();
207
        fire();
202
    }
208
    }
203
 
209
 
204
    public void setPaiementValue(Paiement p, int v) {
210
    public void setPaiementValue(Paiement p, int v) {
205
        if (p.getType() == Paiement.SOLDE) {
211
        if (p.getType() == Paiement.SOLDE) {
206
            int soldeInCents = getClient().getSolde().movePointRight(2).intValue();
212
            int soldeInCents = getClient().getSolde().movePointRight(2).intValue();
207
            if (v > soldeInCents) {
213
            if (v > soldeInCents) {
208
                v = soldeInCents;
214
                v = soldeInCents;
209
            }
215
            }
210
        }
216
        }
211
        p.setMontantInCents(v);
217
        p.setMontantInCents(v);
212
        fire();
218
        fire();
213
        this.setLCD("Paiement " + p.getTypeAsString().replace('è', 'e').replace('é', 'e'), TicketCellRenderer.centsToString(p.getMontantInCents()), 0);
219
        this.setLCD("Paiement " + p.getTypeAsString().replace('è', 'e').replace('é', 'e'), TicketCellRenderer.centsToString(p.getMontantInCents()), 0);
214
        this.setLCDDefaultDisplay(3);
220
        this.setLCDDefaultDisplay(3);
215
    }
221
    }
216
 
222
 
217
    // Totaux
223
    // Totaux
218
    public int getTotal() {
224
    public int getTotal() {
219
        return this.t.getTotalInCents();
225
        return this.t.getTotalInCents();
220
    }
226
    }
221
 
227
 
222
    public int getPaidTotal() {
228
    public int getPaidTotal() {
223
        return this.t.getPaidTotal();
229
        return this.t.getPaidTotal();
224
    }
230
    }
225
 
231
 
226
    //
232
    //
227
 
233
 
228
    public List<Pair<Article, Integer>> getItems() {
234
    public List<TicketItem> getItems() {
229
        return this.t.getArticles();
235
        return this.t.getItems();
230
    }
236
    }
231
 
237
 
232
    public int getItemCount(Article article) {
238
    public BigDecimal getItemCount(Article article) {
233
        return this.t.getItemCount(article);
239
        return this.t.getItemCount(article);
234
    }
240
    }
235
 
241
 
236
    public void clearArticle(Article article) {
242
    public void clearArticle(Article article) {
237
        this.t.clearArticle(article);
243
        this.t.clearArticle(article);
238
        this.setArticleSelected(null);
244
        this.setTicketItemSelected(null);
239
    }
245
    }
240
 
246
 
241
    public void setArticleCount(Article article, int count) {
247
    public void setArticleCount(Article article, BigDecimal count) {
242
        this.t.setArticleCount(article, count);
248
        this.t.setArticleCount(article, count);
243
        this.setArticleSelected(null);
249
        this.setArticleSelected(null);
244
    }
250
    }
245
 
251
 
246
    @Override
252
    @Override
247
    public void barcodeRead(String code) {
253
    public void barcodeRead(String code) {
248
        System.err.println("CaisseControler.barcodeRead() barcode : " + code);
254
        System.err.println("CaisseControler.barcodeRead() barcode : " + code);
249
        if (code.equalsIgnoreCase("especes")) {
255
        if (code.equalsIgnoreCase("especes")) {
250
            autoFillPaiement(this.p1);
256
            autoFillPaiement(this.p1);
251
 
257
 
252
        } else if (code.equalsIgnoreCase("cb")) {
258
        } else if (code.equalsIgnoreCase("cb")) {
253
            autoFillPaiement(this.p2);
259
            autoFillPaiement(this.p2);
254
 
260
 
255
        } else if (code.equalsIgnoreCase("cheque")) {
261
        } else if (code.equalsIgnoreCase("cheque")) {
256
            autoFillPaiement(this.p3);
262
            autoFillPaiement(this.p3);
257
 
263
 
258
        } else if (code.equalsIgnoreCase("annuler")) {
264
        } else if (code.equalsIgnoreCase("annuler")) {
259
            if (this.articleSelected != null) {
265
            if (this.articleSelected != null) {
260
                this.clearArticle(this.articleSelected);
266
                this.clearArticle(this.articleSelected);
261
 
-
 
262
            } else {
-
 
263
                if (this.paiementSelected != null) {
267
            } else if (this.paiementSelected != null) {
264
                    this.paiementSelected.setMontantInCents(0);
268
                this.paiementSelected.setMontantInCents(0);
265
                    // setPaiementSelected(null);
-
 
266
                    fire();
269
                fire();
267
                }
270
            }
268
 
-
 
269
            }
-
 
270
        } else if (code.equalsIgnoreCase("valider")) {
271
        } else if (code.equalsIgnoreCase("valider")) {
271
 
272
 
272
        } else if (code.equalsIgnoreCase("facture")) {
273
        } else if (code.equalsIgnoreCase("facture")) {
273
 
274
 
274
        } else if (code.equalsIgnoreCase("ticket")) {
275
        } else if (code.equalsIgnoreCase("ticket")) {
275
 
276
 
276
        } else {
277
        } else {
277
            Article a = Article.getArticleFromBarcode(code);
278
            Article a = Article.getArticleFromBarcode(code);
278
            if (a != null) {
279
            if (a != null) {
279
                System.err.println("CaisseControler.barcodeRead() barcode : " + code + " : product found : " + a.getName());
280
                System.err.println("CaisseControler.barcodeRead() barcode : " + code + " : product found : " + a.getName());
280
                this.incrementArticle(a);
281
                this.incrementArticle(a);
281
                this.setArticleSelected(a);
282
                this.setArticleSelected(a);
282
            } else {
283
            } else {
283
                System.err.println("CaisseControler.barcodeRead() barcode : " + code + " : no product found");
284
                System.err.println("CaisseControler.barcodeRead() barcode : " + code + " : no product found");
284
                Ticket t = Ticket.getTicketFromCode(code, this.caisseFrame.getFiles());
285
                Ticket t = Ticket.getTicketFromCode(code, this.caisseFrame.getFiles());
285
                if (t != null) {
286
                if (t != null) {
286
                    System.err.println("CaisseControler.barcodeRead() barcode : " + code + " : receipt found :" + t.getNumber());
287
                    System.err.println("CaisseControler.barcodeRead() barcode : " + code + " : receipt found :" + t.getNumber());
287
                    caisseFrame.showTickets(t);
288
                    this.caisseFrame.showTickets(t);
288
                }
289
                }
289
            }
290
            }
290
        }
291
        }
291
 
292
 
292
    }
293
    }
293
 
294
 
294
    void autoFillPaiement(Paiement p) {
295
    void autoFillPaiement(Paiement p) {
295
        int nouveauMontant = getTotal() - getPaidTotal() + p.getMontantInCents();
296
        int nouveauMontant = getTotal() - getPaidTotal() + p.getMontantInCents();
296
        if (p.getType() == Paiement.SOLDE) {
297
        if (p.getType() == Paiement.SOLDE) {
297
            int soldeInCents = getClient().getSolde().movePointRight(2).intValue();
298
            int soldeInCents = getClient().getSolde().movePointRight(2).intValue();
298
            if (nouveauMontant > soldeInCents) {
299
            if (nouveauMontant > soldeInCents) {
299
                nouveauMontant = soldeInCents;
300
                nouveauMontant = soldeInCents;
300
            }
301
            }
301
        }
302
        }
302
        p.setMontantInCents(nouveauMontant);
303
        p.setMontantInCents(nouveauMontant);
303
        setPaiementSelected(p);
304
        setPaiementSelected(p);
304
        this.setLCD("Paiement " + p.getTypeAsString(), TicketCellRenderer.centsToString(p.getMontantInCents()), 0);
305
        this.setLCD("Paiement " + p.getTypeAsString(), TicketCellRenderer.centsToString(p.getMontantInCents()), 0);
305
        this.setLCDDefaultDisplay(3);
306
        this.setLCDDefaultDisplay(3);
306
    }
307
    }
307
 
308
 
308
    void addBarcodeListener(BarcodeListener l) {
309
    void addBarcodeListener(BarcodeListener l) {
309
        this.r.addBarcodeListener(l);
310
        this.r.addBarcodeListener(l);
310
    }
311
    }
311
 
312
 
312
    public boolean canAddPaiement(int type) {
313
    public boolean canAddPaiement(int type) {
313
        final int paiementCount = this.t.getPaiements().size();
314
        final int paiementCount = this.t.getPaiements().size();
314
        if (paiementCount >= 6)
315
        if (paiementCount >= 6)
315
            return false;
316
            return false;
316
        for (int i = 0; i < paiementCount; i++) {
317
        for (int i = 0; i < paiementCount; i++) {
317
            Paiement p = this.t.getPaiements().get(i);
318
            Paiement p = this.t.getPaiements().get(i);
318
            if (p.getType() == type && p.getMontantInCents() != 0) {
319
            if (p.getType() == type && p.getMontantInCents() != 0) {
319
                return false;
320
                return false;
320
            }
321
            }
321
        }
322
        }
322
 
323
 
323
        return true;
324
        return true;
324
    }
325
    }
325
 
326
 
326
    @Override
327
    @Override
327
    public void keyReceived(KeyEvent ee) {
328
    public void keyReceived(KeyEvent ee) {
328
 
-
 
-
 
329
        // nothing
329
    }
330
    }
330
 
331
 
331
    public static String getCents(int cents) {
332
    public static String getCents(int cents) {
332
        String s = String.valueOf(Math.abs(cents) % 100);
333
        String s = String.valueOf(Math.abs(cents) % 100);
333
        if (s.length() < 2) {
334
        if (s.length() < 2) {
334
            s = "0" + s;
335
            s = "0" + s;
335
        }
336
        }
336
        return s;
337
        return s;
337
    }
338
    }
338
 
339
 
339
    public static String getEuros(int cents) {
340
    public static String getEuros(int cents) {
340
        String s = String.valueOf(cents / 100);
341
        return String.valueOf(cents / 100);
341
 
-
 
342
        return s;
-
 
343
    }
342
    }
344
 
343
 
345
    public Ticket saveAndClearTicket(final RegisterFiles files, final SQLElementDirectory dir) throws IOException, SQLException {
344
    public Ticket saveAndClearTicket(final RegisterFiles files, final SQLElementDirectory dir) throws IOException, SQLException {
346
        if (!this.isTicketValid())
345
        if (!this.isTicketValid())
347
            return null;
346
            return null;
348
        this.t.setCreationCal(Calendar.getInstance());
347
        this.t.setCreationCal(Calendar.getInstance());
349
        final String fileHash = this.t.save(files, dir);
348
        final String fileHash = this.t.save(files, dir);
350
        final Ticket res = this.t;
349
        final Ticket res = this.t;
351
        final int newIndex = this.t.getNumber() + 1;
350
        final int newIndex = this.t.getNumber() + 1;
352
        t = new Ticket(getPOSConf().getPosID(), newIndex, fileHash);
351
        this.t = new Ticket(getPOSConf().getPosID(), newIndex, fileHash);
353
        p1 = new Paiement(Paiement.ESPECES);
352
        this.p1 = new Paiement(Paiement.ESPECES);
354
        p2 = new Paiement(Paiement.CB);
353
        this.p2 = new Paiement(Paiement.CB);
355
        p3 = new Paiement(Paiement.CHEQUE);
354
        this.p3 = new Paiement(Paiement.CHEQUE);
356
        this.t.addPaiement(this.p1);
355
        this.t.addPaiement(this.p1);
357
        this.t.addPaiement(this.p2);
356
        this.t.addPaiement(this.p2);
358
        this.t.addPaiement(this.p3);
357
        this.t.addPaiement(this.p3);
359
        this.setPaiementSelected(null);
358
        this.setPaiementSelected(null);
360
        this.setArticleSelected(null);
359
        this.setArticleSelected(null);
361
        client = Client.NONE;
360
        this.client = Client.NONE;
362
        return res;
361
        return res;
363
    }
362
    }
364
 
363
 
365
    public int getTicketNumber() {
364
    public int getTicketNumber() {
366
        return this.t.getNumber();
365
        return this.t.getNumber();
367
    }
366
    }
368
 
367
 
369
    public void openDrawer() {
368
    public void openDrawer() {
370
        try {
369
        try {
371
            final TicketPrinter prt = getPOSConf().getTicketPrinterConfiguration1().createTicketPrinter();
370
            final TicketPrinter prt = getPOSConf().getTicketPrinterConfiguration1().createTicketPrinter();
372
            prt.openDrawer();
371
            prt.openDrawer();
373
        } catch (Exception e) {
372
        } catch (Exception e) {
374
            e.printStackTrace();
373
            e.printStackTrace();
375
        }
374
        }
376
 
375
 
377
    }
376
    }
378
 
377
 
379
    public void switchListMode() {
378
    public void switchListMode() {
380
        caisseFrame.mainPanel.switchListMode();
379
        this.caisseFrame.mainPanel.switchListMode();
381
 
380
 
382
    }
381
    }
383
 
382
 
384
    public void setLCD(final String line1, final String line2, final int delay) {
383
    public void setLCD(final String line1, final String line2, final int delay) {
385
        final TimerTask task = new TimerTask() {
384
        final TimerTask task = new TimerTask() {
386
            @Override
385
            @Override
387
            public void run() {
386
            public void run() {
388
                try {
387
                try {
389
                    lcd.setMessage(line1, line2);
388
                    CaisseControler.this.lcd.setMessage(line1, line2);
390
                } catch (Exception e) {
389
                } catch (Exception e) {
391
                    e.printStackTrace();
390
                    e.printStackTrace();
392
                }
391
                }
393
            }
392
            }
394
        };
393
        };
395
        final Timer timer = new Timer("LCD : " + line1, true);
394
        final Timer timer = new Timer("LCD : " + line1, true);
396
        timer.schedule(task, delay * 1000);
395
        timer.schedule(task, delay * 1000L);
397
 
396
 
398
    }
397
    }
399
 
398
 
400
    public void setLCDDefaultDisplay(int delay) {
399
    public void setLCDDefaultDisplay(int delay) {
401
        if (t.getTotalInCents() > 0) {
400
        if (this.t.getTotalInCents() > 0) {
402
            int count = 0;
401
            int count = 0;
403
            final List<Pair<Article, Integer>> articles = t.getArticles();
402
            final List<TicketItem> articles = this.t.getItems();
404
            for (Pair<Article, Integer> pair : articles) {
403
            for (TicketItem pair : articles) {
-
 
404
                Article a = pair.getArticle();
-
 
405
                if (a.getSalesUnit() == null) {
405
                count += pair.getSecond();
406
                    count += pair.getQty().intValue();
-
 
407
                } else {
-
 
408
                    count++;
-
 
409
                }
406
            }
410
            }
407
            String line1;
411
            String line1;
408
            if (count == 1) {
412
            if (count == 1) {
409
                line1 = "1 article";
413
                line1 = "1 article";
410
            } else {
414
            } else {
411
                line1 = count + " articles";
415
                line1 = count + " articles";
412
            }
416
            }
413
            int cents = t.getTotalInCents();
417
            int cents = this.t.getTotalInCents();
414
            setLCD(line1, "Total : " + TicketCellRenderer.centsToString(cents), delay);
418
            setLCD(line1, "Total : " + TicketCellRenderer.centsToString(cents), delay);
415
        } else {
419
        } else {
416
            setLCD(getPOSConf().getLCDLine1(), getPOSConf().getLCDLine2(), delay);
420
            setLCD(getPOSConf().getLCDLine1(), getPOSConf().getLCDLine2(), delay);
417
        }
421
        }
418
    }
422
    }
419
 
423
 
420
    public void sendCBRequest(final Paiement p) {
424
    public void sendCBRequest(final Paiement p) {
421
 
425
 
422
        final String creditCardPort = getPOSConf().getCreditCardPort();
426
        final String creditCardPort = getPOSConf().getCreditCardPort();
423
        if (creditCardPort != null && creditCardPort.trim().length() > 2) {
427
        if (creditCardPort != null && creditCardPort.trim().length() > 2) {
424
            final Thread t = new Thread(new Runnable() {
428
            final Thread thread = new Thread(new Runnable() {
425
 
429
 
426
                @Override
430
                @Override
427
                public void run() {
431
                public void run() {
428
                    try {
432
                    try {
429
                        ConcertProtocol cp = new ConcertProtocol(creditCardPort);
433
                        ConcertProtocol cp = new ConcertProtocol(creditCardPort);
430
                        boolean ok = cp.sendCardPayment(p.getMontantInCents(), ConcertProtocol.CURRENCY_EUR);
434
                        boolean ok = cp.sendCardPayment(p.getMontantInCents(), ConcertProtocol.CURRENCY_EUR);
431
                        if (ok) {
435
                        if (ok) {
432
                            JOptionPane.showMessageDialog(null, "Paiement CB OK");
436
                            JOptionPane.showMessageDialog(null, "Paiement CB OK");
433
                        } else {
437
                        } else {
434
                            JOptionPane.showMessageDialog(null, "Erreur paiement CB");
438
                            JOptionPane.showMessageDialog(null, "Erreur paiement CB");
435
                        }
439
                        }
436
                    } catch (Throwable ex) {
440
                    } catch (Throwable ex) {
437
                        JOptionPane.showMessageDialog(null, "Erreur terminal CB");
441
                        JOptionPane.showMessageDialog(null, "Erreur terminal CB");
438
                    }
442
                    }
439
                }
443
                }
440
            });
444
            });
441
            t.setDaemon(true);
445
            thread.setDaemon(true);
442
            t.start();
446
            thread.start();
443
 
447
 
444
        }
448
        }
445
 
449
 
446
    }
450
    }
447
 
451
 
448
    public void setArticleHT(Article article, BigDecimal ht) {
452
    public void setArticleHT(TicketItem item, BigDecimal ht) {
449
        Article existingArticle = null;
-
 
450
        final List<Pair<Article, Integer>> articles = t.getArticles();
453
        final Article newArticle = new Article(item.getArticle());
451
        for (Pair<Article, Integer> pair : articles) {
-
 
452
            final Article a = pair.getFirst();
454
        newArticle.updatePriceWithoutTax(ht);
453
            if (a.getId() == article.getId()) {
-
 
454
                if (article.getPriceWithoutTax().doubleValue() == a.getPriceWithoutTax().doubleValue()) {
-
 
455
                    existingArticle = a;
-
 
456
                    break;
-
 
457
                }
-
 
458
            }
-
 
459
        }
-
 
460
        if (existingArticle != null) {
455
        item.setArticle(newArticle);
461
            existingArticle.updatePriceWithoutTax(ht);
-
 
462
            fire();
456
        fire();
463
        }
457
    }
464
    }
-
 
465
 
458
 
466
    public void openPriceEditor(Article article) {
459
    public void openPriceEditor(TicketItem item) {
467
        caisseFrame.showPriceEditor(article, this);
460
        this.caisseFrame.showPriceEditor(item, this);
468
    }
461
    }
469
 
462
 
470
    public void enableBarcodeReader() {
463
    public void enableBarcodeReader() {
471
        this.r.setEnabled(true);
464
        this.r.setEnabled(true);
472
    }
465
    }
473
 
466
 
474
    public void disableBarcodeReader() {
467
    public void disableBarcodeReader() {
475
        this.r.setEnabled(false);
468
        this.r.setEnabled(false);
476
    }
469
    }
477
 
470
 
478
    public boolean isTicketValid() {
471
    public boolean isTicketValid() {
479
        return (!this.t.getArticles().isEmpty()) && ((this.getTotal() >= 0 && this.getPaidTotal() >= this.getTotal()) || (this.getTotal() < 0 && this.getPaidTotal() == this.getTotal()));
472
        return (!this.t.getItems().isEmpty()) && ((this.getTotal() >= 0 && this.getPaidTotal() >= this.getTotal()) || (this.getTotal() < 0 && this.getPaidTotal() == this.getTotal()));
480
    }
473
    }
481
 
474
 
482
    public Set<Integer> loadFavoriteProductsIds() {
475
    public Set<Integer> loadFavoriteProductsIds() {
483
        final TemplateNXProps nxprops = (TemplateNXProps) TemplateNXProps.getInstance();
476
        final TemplateNXProps nxprops = (TemplateNXProps) TemplateNXProps.getInstance();
484
        final File f = new File(nxprops.getDefaultStringValue(), "favorites.txt");
477
        final File f = new File(nxprops.getDefaultStringValue(), "favorites.txt");
485
        System.out.println("CaisseControler.saveFavoriteProductsIds() loading favorites from " + f.getAbsolutePath());
478
        System.out.println("CaisseControler.saveFavoriteProductsIds() loading favorites from " + f.getAbsolutePath());
486
        final Set<Integer> result = new HashSet<>();
479
        final Set<Integer> result = new HashSet<>();
487
        if (f.exists()) {
480
        if (f.exists()) {
488
            try {
481
            try {
489
                String s = FileUtils.read(f);
482
                String s = FileUtils.read(f);
490
                List<String> sIds = StringUtils.fastSplit(s, ',');
483
                List<String> sIds = StringUtils.fastSplit(s, ',');
491
                for (String string : sIds) {
484
                for (String string : sIds) {
492
                    if (!string.isEmpty()) {
485
                    if (!string.isEmpty()) {
493
                        result.add(Integer.parseInt(string));
486
                        result.add(Integer.parseInt(string));
494
                    }
487
                    }
495
                }
488
                }
496
            } catch (IOException e) {
489
            } catch (IOException e) {
497
                e.printStackTrace();
490
                e.printStackTrace();
498
            }
491
            }
499
        }
492
        }
500
        return result;
493
        return result;
501
    }
494
    }
502
 
495
 
503
    public void saveFavoriteProductsIds(List<Article> products) {
496
    public void saveFavoriteProductsIds(List<Article> products) {
504
        final TemplateNXProps nxprops = (TemplateNXProps) TemplateNXProps.getInstance();
497
        final TemplateNXProps nxprops = (TemplateNXProps) TemplateNXProps.getInstance();
505
        final File f = new File(nxprops.getDefaultStringValue(), "favorites.txt");
498
        final File f = new File(nxprops.getDefaultStringValue(), "favorites.txt");
506
        System.out.println("CaisseControler.saveFavoriteProductsIds() saving favorites to " + f.getAbsolutePath());
499
        System.out.println("CaisseControler.saveFavoriteProductsIds() saving favorites to " + f.getAbsolutePath());
507
        try (FileOutputStream fOut = new FileOutputStream(f);) {
500
        try (FileOutputStream fOut = new FileOutputStream(f);) {
508
            for (Article product : products) {
501
            for (Article product : products) {
509
                fOut.write(String.valueOf(product.getId()).getBytes());
502
                fOut.write(String.valueOf(product.getId()).getBytes());
510
                fOut.write(',');
503
                fOut.write(',');
511
            }
504
            }
512
            fOut.flush();
505
            fOut.flush();
513
        } catch (IOException e) {
506
        } catch (IOException e) {
514
            e.printStackTrace();
507
            e.printStackTrace();
515
        }
508
        }
516
    }
509
    }
-
 
510
 
-
 
511
    public void setTicketItemSelected(TicketItem item) {
-
 
512
        this.ticketItemSelected = item;
-
 
513
        if (item == null) {
-
 
514
            this.articleSelected = null;
-
 
515
        } else {
-
 
516
            this.articleSelected = item.getArticle();
-
 
517
            this.paiementSelected = null;
-
 
518
        }
-
 
519
        fire();
-
 
520
 
-
 
521
    }
-
 
522
 
-
 
523
    public TicketItem getTicketItemSelected() {
-
 
524
        return this.ticketItemSelected;
-
 
525
    }
-
 
526
 
-
 
527
    public void removeTicketItem(TicketItem item) {
-
 
528
        this.t.removeTicketItem(item);
-
 
529
        this.setTicketItemSelected(null);
-
 
530
    }
-
 
531
 
-
 
532
    public void cancel(Ticket ticket) {
-
 
533
        this.t.clear();
-
 
534
        // Annulation du ticket
-
 
535
        for (TicketItem a : ticket.getItems()) {
-
 
536
            final Article article = a.getArticle();
-
 
537
            TicketItem item = new TicketItem(article, a.getQty().multiply(new BigDecimal(-1)));
-
 
538
            this.t.addItem(item);
-
 
539
        }
-
 
540
        for (Paiement p : ticket.getPaiements()) {
-
 
541
            final Paiement paiement = new Paiement(p.getType());
-
 
542
            paiement.setMontantInCents(-1 * p.getMontantInCents());
-
 
543
            this.t.addPaiement(paiement);
-
 
544
        }
-
 
545
 
-
 
546
        this.caisseFrame.showCaisse();
-
 
547
        fire();
-
 
548
    }
517
 
549
 
518
}
550
}