OpenConcerto

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

svn://code.openconcerto.org/openconcerto

Compare Revisions

Regard whitespace Rev 184 → Rev 185

/trunk/OpenConcerto/.classpath
13,7 → 13,6
<classpathentry exported="true" kind="lib" path="lib/jdom-1.1.1.jar"/>
<classpathentry exported="true" kind="lib" path="lib/jgrapht-0.7.3.jar"/>
<classpathentry exported="true" kind="lib" path="lib/jpos111.jar"/>
<classpathentry exported="true" kind="lib" path="lib/ognl-2.6.5.jar"/>
<classpathentry exported="true" kind="lib" path="lib/resolver.jar"/>
<classpathentry exported="true" kind="lib" path="lib/RXTXcomm.jar"/>
<classpathentry kind="lib" path="lib/jcip-annotations.jar"/>
35,8 → 34,8
<classpathentry kind="lib" path="lib/accessors-smart-1.1.jar"/>
<classpathentry kind="lib" path="lib/gson-2.8.1.jar"/>
<classpathentry kind="lib" path="lib/icudata_56.jar"/>
<classpathentry kind="lib" path="lib/javax.mail-1.6.0.jar"/>
<classpathentry kind="lib" path="lib/json-smart-2.2.1.jar"/>
<classpathentry exported="true" kind="lib" path="lib/javax.mail-1.6.0.jar"/>
<classpathentry exported="true" kind="lib" path="lib/json-smart-2.2.1.jar"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.8"/>
<classpathentry kind="lib" path="lib/piccolo-1.04.jar"/>
<classpathentry kind="lib" path="lib/javax.activation-1.1.1.jar"/>
48,5 → 47,6
<classpathentry kind="lib" path="lib/flatlaf-1.2.jar"/>
<classpathentry kind="lib" path="lib/fontbox-2.0.22.jar"/>
<classpathentry kind="lib" path="lib/pdfbox-2.0.22.jar"/>
<classpathentry kind="lib" path="lib/OGNL-3.3.2.ILM.jar"/>
<classpathentry kind="output" path="bin"/>
</classpath>
/trunk/OpenConcerto/jpackage.properties
New file
0,0 → 1,9
# jdk11 is 500 MB, jdk > 14 doesn't have jdk.scripting.nashorn
jreVersion=14
# first stable version of jpackage
jpackageVersion=16
jpackageType.mac=dmg
modules=java.base,java.compiler,java.datatransfer,java.desktop,java.instrument,java.logging,java.management,java.prefs,\
java.scripting,java.security.jgss,java.security.sasl,java.sql,java.xml,\
jdk.jdwp.agent,jdk.crypto.ec,jdk.scripting.nashorn,jdk.localedata
javaOptions=-DredirectToFile=true -Dfwk_sql.debug.undefined_id=true -Dfile.encoding=UTF-8 -Xms100M -Xmx768M
/trunk/OpenConcerto/lib/OGNL-3.3.2.ILM.jar
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/lib/OGNL-3.3.2.ILM.jar
New file
Property changes:
Added: svn:mime-type
+application/octet-stream
\ No newline at end of property
/trunk/OpenConcerto/lib/jOpenDocument-1.4rc2.jar
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/Configuration/Template/Labels/50x50.zpl
New file
0,0 → 1,24
^XA
^CI28
 
^FX Designation
^CF0,24
^FO20,50^FB 380,3,0,L,0^FD${product.name}^FS
 
^FX Traitement
^CF0,22
^FO20,140^FDTraitement : ${product.treatment}^FS
 
^FX Origine
^CF0,22
^FO20,170^FDOrigine : ${product.origin}^FS
 
^FX Numero de lot
^CF0,22
^FO20,200^FDN° de lot : ${product.batch}^FS
^FX EAN
^BY3,2,90
^FO60,250^BEN,80,Y,N^FD${product.ean13}^FS
 
^XZ
/trunk/OpenConcerto/Configuration/Template/Labels/57x32.zpl
New file
0,0 → 1,36
^XA
^CI28
 
^FX HT
^CF0,24
^FO490,20,1^FD${product.price}^FS
^CF0,20
^FO490,45,1^FD€ HT^FS
 
^FX TTC
^CF0,24
^FO490,70,1^FD${product.pricewithtax}^FS
^CF0,20
^FO490,95,1^FD€ TTC^FS
 
^FX Code
^CF0,28
^FO20,126^FB 380,3,0,L,0^FD${product.code}^FS
 
^FX Designation
^CF0,24
^FO20,155^FB480,1,0,L,0^FD${product.name}^FS
 
^FX Couleur
^CF0,18
^FO20,185^FDCouleur : ${product.color}^FS
 
^FX Taille
^CF0,18
^FO310,185^FDTaille : ${product.size}^FS
 
^FX EAN
^BY3,2,75
^FO54,15^BEN,75,Y,N^FD${product.ean13}^FS
 
^XZ
/trunk/OpenConcerto/Configuration/Template/Default/EtatStockInventaire.ods
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/Configuration/Template/Default/LivrePaye.ods
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/Configuration/Template/Default/FichePayeSimplifiee.ods
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/Configuration/Template/Default/EtatRapprochement.odsp
New file
0,0 → 1,9
<odsp>
<spliteveryrow>
<sheet number="0">60</sheet>
</spliteveryrow>
<offset x="0" y ="0"/>
<resize percent="100"/>
 
 
</odsp>
/trunk/OpenConcerto/Configuration/Template/Default/LivrePaye.odsp
2,8 → 2,8
<spliteveryrow>
<sheet number="0">67</sheet>
</spliteveryrow>
<offset x="40" y ="20"/>
<resize percent="85"/>
<offset x="0" y ="0"/>
<resize percent="100"/>
 
 
</odsp>
/trunk/OpenConcerto/Configuration/Template/Default/EtatRapprochement.ods
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/Configuration/Template/Default/EtatRapprochement.ods
New file
Property changes:
Added: svn:mime-type
+application/octet-stream
\ No newline at end of property
/trunk/OpenConcerto/Configuration/Template/Default/RepartitionAnalytique.xml
28,7 → 28,11
<field name="POSTE_NOM" />
</element>
 
<element location="D" type="fill">
<field name="CLASSE" />
</element>
<element location="E" type="fill">
<field name="DEBIT" />
</element>
/trunk/OpenConcerto/Configuration/Template/Default/EtatChargesPaye.odsp
New file
0,0 → 1,9
<odsp>
<spliteveryrow>
<sheet number="0">68</sheet>
</spliteveryrow>
<offset x="0" y ="0"/>
<resize percent="100"/>
 
 
</odsp>
/trunk/OpenConcerto/Configuration/Template/Default/EtatStockInventaire.xml
3,7 → 3,7
<!-- <element location="A3" type="Value" ValueName="DATE">
</element>
-->
<table firstLine="2" endLine="17000" endPageLine="25000" lastColumn="E" table="SAISIE_VENTE_FACTURE">
<table firstLine="2" endLine="-1" endPageLine="25000" lastColumn="E" table="SAISIE_VENTE_FACTURE">
<element location="A" type="fill">
<field name="FAMILLE" />
29,5 → 29,9
<field name="QTE" />
</element>
 
<element location="H" type="fill">
<field name="DEPOT" />
</element>
 
</table>
</contentDocument>
/trunk/OpenConcerto/Configuration/Template/Default/FichePayeSimplifiee.xml
13,11 → 13,11
</field>
</element>
 
<element location="D7" type="fill">
<element location="C7" type="fill">
<field base="Common" table="SOCIETE_COMMON" name="NUMERO_URSSAF" />
</element>
 
<element location="G7" type="fill">
<element location="F7" type="fill">
<field base="Common" table="SOCIETE_COMMON" name="NUM_SIRET" />
</element>
 
114,10 → 114,10
<field name="DETAILS_CONGES" />
</element>
 
<element location="H52" type="fill">
<element location="G52" type="fill">
<field name="COT_SAL" />
</element>
<element location="I52" type="fill">
<element location="H52" type="fill">
<field name="COT_PAT" />
</element>
 
/trunk/OpenConcerto/Configuration/Template/Default/EtatRapprochement.xml
New file
0,0 → 1,45
<?xml version="1.0" encoding="UTF-8" ?>
 
<contentDocument>
<element0 location="A1" type="Value" ValueName="SOCIETE">
</element0>
 
<element0 location="F1" type="Value" ValueName="DATE_EDITION">
</element0>
 
<element0 location="A3" type="Value" ValueName="TITRE">
</element0>
 
<table0 firstLine="6" endLine="60" endPageLine="60" lastColumn="G" base="Societe" table="ECRITURE" pageRef="F3">
<element location="A" type="fill" >
<field base="Societe" name="DATE"/>
</element>
 
<element location="B" type="fill" >
<field base="Societe" name="CODE_JOURNAL"/>
</element>
 
 
<element location="C" type="fill" >
<field base="Societe" name="PIECE"/>
</element>
 
<element location="D" type="fill" maxChar="60" >
<field base="Societe" name="NOM"/>
</element>
 
<element location="E" type="fill">
<field base="Societe" name="DEBIT"/>
</element>
 
<element location="F" type="fill">
<field base="Societe" name="CREDIT"/>
</element>
<element location="G" type="fill">
<field base="Societe" name="SOLDE"/>
</element>
</table0>
 
</contentDocument>
/trunk/OpenConcerto/Configuration/Template/Default/RepartitionAnalytique.odsp
1,9 → 1,7
<odsp>
<spliteveryrow>
<sheet number="0">68</sheet>
<sheet number="0">69</sheet>
</spliteveryrow>
<offset x="40" y ="20"/>
<resize percent="85"/>
 
 
<offset x="0" y ="0"/>
<resize percent="100"/>
</odsp>
/trunk/OpenConcerto/Configuration/Template/Default/EtatVentes.ods
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/Configuration/Template/Default/RepartitionAnalytique.ods
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/src/org/jopendocument/link/OOConnexion.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
27,6 → 27,7
import java.net.URLClassLoader;
import java.security.CodeSource;
import java.security.PermissionCollection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.PropertyPermission;
54,7 → 55,8
}
 
static private final URL[] getURLs(final OOInstallation ooInstall) {
final List<URL> res = ooInstall.getURLs(CollectionUtils.createSet("ridl.jar", "jurt.jar", "juh.jar", "unoil.jar"));
final List<URL> from_v7 = ooInstall.getURLs(Collections.singleton("libreoffice.jar"));
final List<URL> res = from_v7.isEmpty() ? ooInstall.getURLs(CollectionUtils.createSet("ridl.jar", "jurt.jar", "juh.jar", "unoil.jar")) : from_v7;
return res.toArray(new URL[res.size()]);
}
 
/trunk/OpenConcerto/src/org/jopendocument/link/OOInstallation.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
/trunk/OpenConcerto/src/org/jopendocument/link/Component.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/Exercice.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
380,10 → 380,27
 
SQLUpdate.executeMultipleWithBatch(sysRoot, mvtUpdate);
 
// Creation des inserts des écritures sans analytique
final List<SQLInsert> insertsEcrituresSansAnalytique = new ArrayList<>(insertsMouvement.size() * 2);
final List<SQLInsert> insertsEcrituresAvecAnalytique = new ArrayList<>(insertsMouvement.size() * 2);
final List<Ecriture> ecrituresAvecAnalytique = new ArrayList<>(insertsEcrituresAvecAnalytique.size());
final List<SQLInsert> insertsURL = new ArrayList<>(insertsMouvement.size());
for (int i = 0; i < pieces.size(); i++) {
Piece piece = pieces.get(i);
piece.setId(idsPieces.get(i));
for (Mouvement m : piece.getMouvements()) {
if (m.hasURLs()) {
List<MouvementGED> urLs = m.getURLs();
for (MouvementGED urls : urLs) {
insertsURL.add(urls.createInsert(root, user));
}
}
}
}
if (!insertsURL.isEmpty()) {
SQLInsert.executeSimilarInserts(sysRoot, insertsURL, false);
}
 
// Creation des inserts des écritures sans liens ( analytique)
final List<SQLInsert> insertsEcrituresSansLiens = new ArrayList<>(insertsMouvement.size() * 2);
final List<SQLInsert> insertsEcrituresAvecLiens = new ArrayList<>(insertsMouvement.size() * 2);
final List<Ecriture> ecrituresAvecLiens = new ArrayList<>(insertsEcrituresAvecLiens.size());
for (Piece p : pieces) {
final List<Mouvement> mouvements = p.getMouvements();
final int stop = mouvements.size();
391,32 → 408,43
final Mouvement m = mouvements.get(i);
for (Ecriture e : m.getEcritures()) {
if (e.hasAnalytique()) {
insertsEcrituresAvecAnalytique.add(e.createInsert(root, user));
ecrituresAvecAnalytique.add(e);
insertsEcrituresAvecLiens.add(e.createInsert(root, user));
ecrituresAvecLiens.add(e);
} else {
insertsEcrituresSansAnalytique.add(e.createInsert(root, user));
insertsEcrituresSansLiens.add(e.createInsert(root, user));
}
}
 
}
}
if (!insertsEcrituresSansLiens.isEmpty()) {
// Insertions des écritures des mouvements
SQLInsert.executeSimilarInserts(sysRoot, insertsEcrituresSansAnalytique, false);
SQLInsert.executeSimilarInserts(sysRoot, insertsEcrituresSansLiens, false);
}
// Insertions des écritures avec analytique
if (!ecrituresAvecAnalytique.isEmpty()) {
final List<Number> idsEcritues = SQLInsert.executeSimilarInserts(sysRoot, insertsEcrituresAvecAnalytique, true);
if (!ecrituresAvecLiens.isEmpty()) {
final List<Number> idsEcritues = SQLInsert.executeSimilarInserts(sysRoot, insertsEcrituresAvecLiens, true);
// Analytique
final List<SQLInsert> insertsAssociationAnalytique = new ArrayList<>(insertsEcrituresAvecAnalytique.size());
final int size = ecrituresAvecAnalytique.size();
final List<SQLInsert> insertsAssociationAnalytique = new ArrayList<>(insertsEcrituresAvecLiens.size());
final List<SQLInsert> insertsURLs = new ArrayList<>(insertsEcrituresAvecLiens.size());
final int size = ecrituresAvecLiens.size();
for (int i = 0; i < size; i++) {
final Ecriture e = ecrituresAvecAnalytique.get(i);
final Ecriture e = ecrituresAvecLiens.get(i);
e.setId(idsEcritues.get(i));
if (e.hasAnalytique()) {
for (AssociationAnalytique a : e.getAssociationsAnalytiques()) {
insertsAssociationAnalytique.add(a.createInsert(root, user));
}
}
 
}
if (!insertsAssociationAnalytique.isEmpty()) {
SQLInsert.executeSimilarInserts(sysRoot, insertsAssociationAnalytique, false);
}
if (!insertsURLs.isEmpty()) {
SQLInsert.executeSimilarInserts(sysRoot, insertsURLs, false);
}
}
for (Piece p : pieces) {
final List<Mouvement> mouvements = p.getMouvements();
for (Mouvement m : mouvements) {
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtAcompte.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
18,13 → 18,12
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.GestionDevise;
 
import java.sql.SQLException;
import java.util.Date;
 
public final class GenerationMvtAcompte extends GenerationEcritures implements Runnable {
public final class GenerationMvtAcompte extends GenerationEcritures {
 
private int idSalarie;
private long montant;
44,10 → 43,10
this.montant = GestionDevise.parseLongCurrency(String.valueOf(rowAcompte.getFloat("MONTANT")));
SQLRow rowSal = tableSalarie.getRow(this.idSalarie);
this.idMvt = getNewMouvement("ACOMPTE", this.idAcompte, 1, "Acompte " + rowSal.getString("NOM"));
new Thread(GenerationMvtAcompte.this).start();
genereComptaAcompte();
}
 
private void genereComptaAcompte() throws Exception {
private void genereComptaAcompte() throws SQLException {
 
System.out.println("Génération des ecritures du mouvement " + this.idMvt);
 
99,12 → 98,4
 
}
 
public void run() {
 
try {
genereComptaAcompte();
} catch (Exception e) {
ExceptionHandler.handle("Erreur lors de la génération des mouvements", e);
}
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtSaisieVenteFacture.java
16,15 → 16,20
import org.openconcerto.erp.core.common.ui.TotalCalculator;
import org.openconcerto.erp.core.finance.accounting.element.ComptePCESQLElement;
import org.openconcerto.erp.core.finance.accounting.element.JournalSQLElement;
import org.openconcerto.erp.core.finance.payment.element.TypeReglementSQLElement;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.generationDoc.SheetXml;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.generationEcritures.provider.AccountingRecordsProvider;
import org.openconcerto.erp.generationEcritures.provider.AccountingRecordsProviderManager;
import org.openconcerto.erp.model.PrixTTC;
import org.openconcerto.erp.preferences.DefaultNXProps;
import org.openconcerto.erp.preferences.GestionCommercialeGlobalPreferencePanel;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.preferences.SQLPreferences;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.StringUtils;
 
42,6 → 47,7
public class GenerationMvtSaisieVenteFacture extends GenerationEcritures implements Runnable {
 
public static final String ID = "accounting.records.invoice.sales";
public static final String NOT_GEN_ECRITURE = "accounting.invoice.generation.disable";
private static final String source = "SAISIE_VENTE_FACTURE";
public static final Integer journal = Integer.valueOf(JournalSQLElement.VENTES);
private int idSaisieVenteFacture;
99,13 → 105,10
 
SQLRow saisieRow = GenerationMvtSaisieVenteFacture.saisieVFTable.getRow(this.idSaisieVenteFacture);
setRowAnalytiqueSource(saisieRow);
boolean genEcrDisabled = DefaultNXProps.getInstance().getBooleanValue(GenerationMvtSaisieVenteFacture.NOT_GEN_ECRITURE, false);
 
this.putValue("ID_JOURNAL", GenerationMvtSaisieVenteFacture.journal);
SQLRow clientRow = saisieRow.getForeignRow("ID_CLIENT");
 
// Calcul des montants
PrixTTC prixTTC = new PrixTTC(((Long) saisieRow.getObject("T_TTC")).longValue());
// Total des acomptes déjà versés sur la facture
long montantAcompteTTC = 0;
 
int idCompteClient = clientRow.getInt("ID_COMPTE_PCE");
 
Boolean acompte = saisieRow.getBoolean("ACOMPTE");
114,7 → 117,36
} else {
this.nom = "Fact. vente " + saisieRow.getObject("NUMERO").toString();
}
 
boolean typeCaisse = false;
SQLRow modeRegl = saisieRow.getForeignRow("ID_MODE_REGLEMENT");
final SQLRow typeRegRow = modeRegl.getForeignRow("ID_TYPE_REGLEMENT");
final SQLRowAccessor nonEmptyForeign = modeRegl.getNonEmptyForeign("ID_BANQUE");
if (nonEmptyForeign != null && nonEmptyForeign.getTable().contains("TYPE_CAISSE") && nonEmptyForeign.getBoolean("TYPE_CAISSE")) {
typeCaisse = true;
idCompteClient = nonEmptyForeign.getForeignID("ID_COMPTE_PCE");
Number idJournal = nonEmptyForeign.getNonEmptyForeignIDNumber("ID_JOURNAL");
if (idJournal != null) {
this.putValue("ID_JOURNAL", idJournal);
} else {
this.putValue("ID_JOURNAL", JournalSQLElement.CAISSES);
}
this.nom += " (" + typeRegRow.getString("NOM") + ") " + StringUtils.limitLength(clientRow.getString("NOM"), 20);
} else {
this.nom += " " + StringUtils.limitLength(clientRow.getString("NOM"), 20);
}
 
if (SQLPreferences.getMemCached(saisieRow.getTable().getDBRoot()).getBoolean(GestionCommercialeGlobalPreferencePanel.ECRITURE_FACTURE_REF_LIBELLE, false)) {
if (saisieRow.getString("NOM") != null && saisieRow.getString("NOM").trim().length() > 0)
this.nom += " " + StringUtils.limitLength(saisieRow.getString("NOM"), 30);
}
 
 
// Calcul des montants
PrixTTC prixTTC = new PrixTTC(((Long) saisieRow.getObject("T_TTC")).longValue());
// Total des acomptes déjà versés sur la facture
long montantAcompteTTC = 0;
 
this.putValue("NOM", this.nom);
 
// iniatilisation des valeurs de la map
123,7 → 155,7
provider.putLabel(saisieRow, this.mEcritures);
 
this.putValue("DATE", this.date);
this.putValue("ID_JOURNAL", GenerationMvtSaisieVenteFacture.journal);
 
this.putValue("ID_MOUVEMENT", Integer.valueOf(1));
 
// on calcule le nouveau numero de mouvement
176,7 → 208,9
this.putValue("ID_COMPTE_PCE", rowCompl.getForeignID("ID_COMPTE_PCE"));
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", Long.valueOf(taxeC));
if (!genEcrDisabled) {
ajoutEcriture();
}
taxe += taxeC;
// this.putValue("ID_COMPTE_PCE",
// rowCompl.getForeignID("ID_COMPTE_PCE_PRODUITS"));
197,9 → 231,11
this.putValue("ID_COMPTE_PCE", idComptePCE);
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", Long.valueOf(b - taxe));
if (!genEcrDisabled) {
ajoutEcriture();
}
}
}
 
Map<SQLRowAccessor, BigDecimal> tvaMap = calc.getMapHtTVA();
for (SQLRowAccessor rowAc : tvaMap.keySet()) {
208,9 → 244,11
this.putValue("ID_COMPTE_PCE", rowAc.getID());
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", longValue);
if (!genEcrDisabled) {
ajoutEcriture();
}
}
}
 
// compte Clients
 
226,7 → 264,9
}
this.putValue("DEBIT", ttcLongValue);
this.putValue("CREDIT", Long.valueOf(0));
if (!genEcrDisabled) {
ajoutEcriture();
}
 
// TODO Gestion des factures d'acomptes
// Solde des acomptes
303,9 → 343,8
 
if (genereReglement) {
// Génération du reglement
SQLRow modeRegl = saisieRow.getForeignRow("ID_MODE_REGLEMENT");
final SQLRow typeRegRow = modeRegl.getForeignRow("ID_TYPE_REGLEMENT");
String label = this.nom + " (" + typeRegRow.getString("NOM") + ") " + StringUtils.limitLength(clientRow.getString("NOM"), 20);
 
String label = this.nom + " (" + typeRegRow.getString("NOM") + ") ";
int idAvoir = saisieRow.getInt("ID_AVOIR_CLIENT");
if (idAvoir > 1) {
// SQLRow avoirRow = base.getTable("AVOIR_CLIENT").getRow(idAvoir);
312,11 → 351,46
long l = ((Number) saisieRow.getObject("T_AVOIR_TTC")).longValue();
prixTTC = new PrixTTC(((Long) saisieRow.getObject("T_TTC")).longValue() - l);
}
prixTTC = new PrixTTC(saisieRow.getLong("NET_A_PAYER"));
final long totalNet = saisieRow.getLong("NET_A_PAYER");
final SQLRow rowClient;
final SQLRow rowCptTiers;
if (typeCaisse) {
rowClient = null;
rowCptTiers = modeRegl.getForeign("ID_BANQUE").getForeign("ID_COMPTE_PCE");
} else {
rowClient = clientRow;
rowCptTiers = null;
}
final String tiers = clientRow.getString("NOM");
 
if (saisieRow.contains("POURCENT_RG") && saisieRow.getBigDecimal("POURCENT_RG") != null && saisieRow.getBigDecimal("POURCENT_RG").signum() != 0) {
long totalRG = new BigDecimal(totalNet).multiply(saisieRow.getBigDecimal("POURCENT_RG"), DecimalUtils.HIGH_PRECISION).movePointLeft(2).setScale(0, RoundingMode.HALF_UP)
.longValue();
PrixTTC prixRG = new PrixTTC(totalRG);
prixTTC = new PrixTTC(totalNet - totalRG);
if (prixTTC.getLongValue() > 0) {
new GenerationReglementVenteNG(label.trim(), clientRow, prixTTC, this.date, modeRegl, saisieRow, mvtTable.getRow(idMvt));
new GenerationReglementVenteNG(label.trim(), rowClient, prixTTC, this.date, modeRegl, saisieRow, mvtTable.getRow(idMvt), true, false, tiers, rowCptTiers);
}
if (prixRG.getLongValue() > 0) {
SQLRowValues rowValsMdrRg = new SQLRowValues(modeRegl.getTable());
rowValsMdrRg.put("AJOURS", 365);
rowValsMdrRg.put("LENJOUR", 0);
rowValsMdrRg.put("COMPTANT", Boolean.FALSE);
rowValsMdrRg.put("FIN_MOIS", Boolean.FALSE);
rowValsMdrRg.put("DATE_FACTURE", Boolean.TRUE);
rowValsMdrRg.put("RG", Boolean.TRUE);
rowValsMdrRg.put("ID_TYPE_REGLEMENT", TypeReglementSQLElement.INDEFINI);
final SQLRow rowMdrRG = rowValsMdrRg.commit();
new GenerationReglementVenteNG(label.trim(), rowClient, prixRG, this.date, rowMdrRG, saisieRow, mvtTable.getRow(idMvt), true, false, tiers, rowCptTiers);
}
} else {
prixTTC = new PrixTTC(totalNet);
if (prixTTC.getLongValue() > 0) {
new GenerationReglementVenteNG(label.trim(), rowClient, prixTTC, this.date, modeRegl, saisieRow, mvtTable.getRow(idMvt), true, false, tiers, rowCptTiers);
}
}
 
}
// Mise à jour de mouvement associé à la facture
 
SQLRowValues valSasieVF = new SQLRowValues(GenerationMvtSaisieVenteFacture.saisieVFTable);
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/MouvementGED.java
New file
0,0 → 1,48
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.generationEcritures;
 
import org.openconcerto.erp.core.edm.Attachment;
import org.openconcerto.sql.model.DBRoot;
import org.openconcerto.sql.model.SQLInsert;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.users.User;
 
public class MouvementGED {
private String url;
private Mouvement mvt;
 
public MouvementGED(String url) {
this.url = url;
}
 
public void setEcriture(Mouvement mvt) {
this.mvt = mvt;
}
 
public SQLInsert createInsert(DBRoot root, User user) {
final SQLInsert insert = new SQLInsert();
final SQLTable table = root.getTable("ATTACHMENT");
insert.add(table.getField("SOURCE_TABLE"), "MOUVEMENT");
insert.add(table.getField("SOURCE_ID"), this.mvt.getId().intValue());
insert.add(table.getField("NAME"), this.url);
insert.add(table.getField("FILENAME"), this.url);
insert.add(table.getField("MIMETYPE"), Attachment.MIMETYPE_URL);
insert.add(table.getField("FILESIZE"), 0);
insert.add(table.getField("STORAGE_PATH"), "");
insert.add(table.getField("STORAGE_FILENAME"), "");
return insert;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtFichePaye.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
57,7 → 57,7
 
private Map<String, SQLTable> mapTableSource = new HashMap<String, SQLTable>();
 
public GenerationMvtFichePaye(int[] idFichePaye, String mois, String annee) throws SQLException {
public GenerationMvtFichePaye(int[] idFichePaye, String mois, String annee, Date d) throws SQLException {
 
setRowAnalytiqueSource(null);
SQLTable tableNet = Configuration.getInstance().getBase().getTable("RUBRIQUE_NET");
73,6 → 73,7
this.idFichePaye = idFichePaye;
this.annee = annee;
this.mois = mois;
this.date = d;
this.idMvt = getNewMouvement("", 1, 1, "Paye " + this.mois + " " + this.annee);
new Thread(GenerationMvtFichePaye.this).start();
}
98,7 → 99,7
// SQLRow rowFiche =
// Configuration.getInstance().getBase().getTable("FICHE_PAYE").getRow(this.idFichePaye);
// iniatilisation des valeurs de la map
this.date = new Date();
// this.date = new Date();
 
// SQLRow rowMois = tableMois.getRow(rowFiche.getInt("ID_MOIS"));
// SQLRow rowSal = tableSalarie.getRow(rowFiche.getInt("ID_SALARIE"));
348,15 → 349,19
 
Tuple2<Integer, Integer> t = mapCaisse.get(idCaisse);
// on recupere les comptes tiers et charge de la caisse associée
int idCompteCharge = (t == null ? ComptePCESQLElement.getId("645") : t.get0());
// }
int idCompteCharge;
if (rowSource.getString("NUMERO_COMPTE_PCE_CHARGES") != null && rowSource.getString("NUMERO_COMPTE_PCE_CHARGES").trim().length() > 0) {
idCompteCharge = ComptePCESQLElement.getId(rowSource.getString("NUMERO_COMPTE_PCE_CHARGES"));
} else {
idCompteCharge = (t == null ? ComptePCESQLElement.getId("645") : t.get0());
}
int idCompteTiers;
if (rowSource.getString("NUMERO_COMPTE_PCE") != null && rowSource.getString("NUMERO_COMPTE_PCE").trim().length() > 0) {
idCompteTiers = ComptePCESQLElement.getId(rowSource.getString("NUMERO_COMPTE_PCE"));
} else {
idCompteTiers = (t == null ? ComptePCESQLElement.getId("437") : t.get1());
}
 
// int idCompteTiers = rowCaisse.getInt("ID_COMPTE_PCE_TIERS");
// if (idCompteTiers <= 1) {
int idCompteTiers = (t == null ? ComptePCESQLElement.getId("437") : t.get1());
// int idCompteTiers = ComptePCESQLElement.getId("437");
// }
 
// Cotisations sal.
if (row.getObject("MONTANT_SAL_DED") != null && row.getFloat("MONTANT_SAL_DED") != 0) {
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtReglementFactureFournisseur.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
38,7 → 38,7
import java.util.Map;
 
// FIXME mettre toute les generations dans des threads à part
public final class GenerationMvtReglementFactureFournisseur extends GenerationEcritures implements Runnable {
public final class GenerationMvtReglementFactureFournisseur extends GenerationEcritures {
 
private int idfacture;
 
50,13 → 50,13
private static final SQLRow rowPrefsCompte = tablePrefCompte.getRow(2);
private int idPere = 1; // Id du mouvement pere
 
public GenerationMvtReglementFactureFournisseur(int idFacture, int idMvt) {
public GenerationMvtReglementFactureFournisseur(int idFacture, int idMvt) throws SQLException {
this.idfacture = idFacture;
this.idPere = idMvt;
new Thread(GenerationMvtReglementFactureFournisseur.this).start();
genereReglement();
}
 
private void genereReglement() throws Exception {
private void genereReglement() throws SQLException {
 
System.out.println("Génération des ecritures du reglement du mouvement " + this.idMvt);
 
249,7 → 249,7
 
public void run() {
try {
genereReglement();
} catch (Exception e) {
ExceptionHandler.handle("Erreur pendant la générations des écritures comptables", e);
e.printStackTrace();
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtSaisieKm.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
61,7 → 61,7
getNewMouvement(GenerationMvtSaisieKm.source, this.idSaisieKm, 1, rowValsPiece);
 
// gnération des ecritures
SQLTable tableElt = Configuration.getInstance().getRoot().findTable("SAISIE_KM_ELEMENT");
SQLTable tableElt = table.getDBRoot().findTable("SAISIE_KM_ELEMENT");
List<SQLRow> set = saisieRow.getReferentRows(tableElt);
 
SQLTable tableAssoc = Configuration.getInstance().getRoot().findTable("ASSOCIATION_ANALYTIQUE");
70,6 → 70,9
 
int idCpt = ComptePCESQLElement.getId(rowElement.getString("NUMERO"), rowElement.getString("NOM"));
 
if (ecritureTable.contains("DATE_ECHEANCE") && table.getDBRoot().findTable("SAISIE_KM_ELEMENT").contains("DATE_ECHEANCE")) {
this.putValue("DATE_ECHEANCE", rowElement.getObject("DATE_ECHEANCE"));
}
// Ajout de l'écriture
this.putValue("ID_COMPTE_PCE", new Integer(idCpt));
this.putValue("NOM", rowElement.getString("NOM_ECRITURE"));
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/provider/SalesInvoiceAccountingRecordsProvider.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
15,9 → 15,11
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.generationEcritures.GenerationMvtSaisieVenteFacture;
import org.openconcerto.erp.preferences.GestionCommercialeGlobalPreferencePanel;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.preferences.SQLPreferences;
import org.openconcerto.utils.StringUtils;
 
import java.util.Map;
40,7 → 42,21
} else {
nom = "Fact. vente " + rowSource.getObject("NUMERO").toString();
}
SQLRowAccessor modeRegl = rowSource.getForeign("ID_MODE_REGLEMENT");
final SQLRowAccessor typeRegRow = modeRegl.getForeign("ID_TYPE_REGLEMENT");
final SQLRowAccessor nonEmptyForeign = modeRegl.getNonEmptyForeign("ID_BANQUE");
if (nonEmptyForeign != null && nonEmptyForeign.getTable().contains("TYPE_CAISSE") && nonEmptyForeign.getBoolean("TYPE_CAISSE")) {
 
nom += " (" + typeRegRow.getString("NOM") + ") ";
}
 
nom += " " + StringUtils.limitLength(rowSource.getForeign("ID_CLIENT").getString("NOM"), 20);
 
if (SQLPreferences.getMemCached(rowSource.getTable().getDBRoot()).getBoolean(GestionCommercialeGlobalPreferencePanel.ECRITURE_FACTURE_REF_LIBELLE, false)) {
if (rowSource.getString("NOM") != null && rowSource.getString("NOM").trim().length() > 0)
nom += " " + StringUtils.limitLength(rowSource.getString("NOM"), 30);
}
 
values.put("NOM", nom);
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/Mouvement.java
25,6 → 25,7
public class Mouvement {
private String numero;
private List<Ecriture> ecritures = new ArrayList<>();
private List<MouvementGED> gedURLs;
private Number id;
private BigDecimal debit = BigDecimal.ZERO;
private BigDecimal credit = BigDecimal.ZERO;
62,6 → 63,22
return this.id;
}
 
public List<MouvementGED> getURLs() {
return this.gedURLs;
}
 
public void addURL(MouvementGED e) {
if (this.gedURLs == null) {
this.gedURLs = new ArrayList<>();
}
e.setEcriture(this);
this.gedURLs.add(e);
}
 
public boolean hasURLs() {
return this.gedURLs != null;
}
 
SQLInsert createInsert(DBRoot root, User user) {
final SQLInsert insert = new SQLInsert();
final SQLTable table = root.getTable("MOUVEMENT");
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationEcritures.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
482,7 → 482,28
final SQLTable tablePrefCompte = Configuration.getInstance().getRoot().findTable("PREFS_COMPTE");
final SQLRow rowPrefsCompte = SQLBackgroundTableCache.getInstance().getCacheForTable(tablePrefCompte).getRowFromId(2);
SQLRow rowDefaultCptPort;
if (achat) {
if (rowTVAPort.getFloat("TAUX") > 0) {
rowDefaultCptPort = cacheCompte.getRowFromId(rowPrefsCompte.getForeignID("ID_COMPTE_PCE_PORT_SOUMIS_ACHAT"));
if (rowDefaultCptPort == null || rowDefaultCptPort.isUndefined()) {
try {
rowDefaultCptPort = ComptePCESQLElement.getRowComptePceDefault("PortAchatSoumisTVA");
} catch (Exception e) {
e.printStackTrace();
}
}
} else {
rowDefaultCptPort = cacheCompte.getRowFromId(rowPrefsCompte.getForeignID("ID_COMPTE_PCE_PORT_NON_SOUMIS_ACHAT"));
if (rowDefaultCptPort == null || rowDefaultCptPort.isUndefined()) {
try {
rowDefaultCptPort = ComptePCESQLElement.getRowComptePceDefault("PortAchatNonSoumisTVA");
} catch (Exception e) {
e.printStackTrace();
}
}
}
} else {
if (rowTVAPort.getFloat("TAUX") > 0) {
rowDefaultCptPort = cacheCompte.getRowFromId(rowPrefsCompte.getForeignID("ID_COMPTE_PCE_PORT_SOUMIS"));
if (rowDefaultCptPort == null || rowDefaultCptPort.isUndefined()) {
try {
501,6 → 522,7
}
}
}
}
final SQLRowValues rowValsArt = rowValsPort.putRowValues("ID_ARTICLE");
rowValsArt.put(achat ? "ID_COMPTE_PCE_ACHAT" : "ID_COMPTE_PCE", rowDefaultCptPort.getID());
rowValsArt.put("ID_TAXE_COMPLEMENTAIRE", null);
606,8 → 628,14
SQLRow rowJournal = rowBanque.getForeignRow("ID_JOURNAL");
this.mEcritures.put("ID_JOURNAL", rowJournal.getID());
}
} else if (sqlRow.getTable().contains("ID_TYPE_REGLEMENT") && !sqlRow.isForeignEmpty("ID_TYPE_REGLEMENT")) {
SQLRow rowType = sqlRow.getForeignRow("ID_TYPE_REGLEMENT");
if (rowType.getTable().contains("ID_JOURNAL") && !rowType.isForeignEmpty("ID_JOURNAL")) {
SQLRow rowJournal = rowType.getForeignRow("ID_JOURNAL");
this.mEcritures.put("ID_JOURNAL", rowJournal.getID());
}
}
}
 
/**
* Définit le compte en fonction de la banque sélectionnée
615,7 → 643,7
* @param sqlRow sqlRow contenant la foreignKey Banque
* @throws Exception
*/
protected void fillCompteBanqueFromRow(SQLRow sqlRow, String defaultProps, boolean achat) throws Exception {
protected void fillCompteBanqueFromRow(SQLRow sqlRow, String defaultProps, boolean achat) throws SQLException {
int idPce = -1;
if (sqlRow.getTable().contains("ID_TYPE_REGLEMENT")) {
idPce = sqlRow.getForeign("ID_TYPE_REGLEMENT").getInt("ID_COMPTE_PCE_" + (achat ? "FOURN" : "CLIENT"));
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/Ecriture.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
31,6 → 31,7
private BigDecimal credit;
private Mouvement mouvement;
private String nom;
private String nomPieceCommerciale;
private String compteNumero;
private String compteNom;
private Number compteID;
50,6 → 51,7
this.date = date;
this.debit = debit;
this.credit = credit;
this.nomPieceCommerciale = "";
}
 
public SQLInsert createInsert(DBRoot root, User user) {
79,7 → 81,7
insert.add(table.getField("ID_JOURNAL"), this.journalID);
insert.add(table.getField("JOURNAL_NOM"), this.journalNom);
insert.add(table.getField("JOURNAL_CODE"), this.journalCode);
insert.add(table.getField("NOM_PIECE"), this.mouvement.getPiece().getNom());
insert.add(table.getField("NOM_PIECE"), this.nomPieceCommerciale);
insert.add(table.getField("ID_USER_COMMON_CREATE"), user.getId());
insert.add(table.getField("ID_USER_COMMON_MODIFY"), user.getId());
insert.add(table.getField("CLOTURE"), this.cloture);
104,6 → 106,14
this.dateLettrage = dateLettrage;
}
 
public void setNomPieceCommerciale(String nomPieceCommerciale) {
this.nomPieceCommerciale = nomPieceCommerciale;
}
 
public String getNomPieceCommerciale() {
return this.nomPieceCommerciale;
}
 
public void setLettrage(String lettrage) {
this.lettrage = lettrage;
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtAvoirClient.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
19,6 → 19,7
import org.openconcerto.erp.core.finance.accounting.element.JournalSQLElement;
import org.openconcerto.erp.generationEcritures.provider.AccountingRecordsProvider;
import org.openconcerto.erp.generationEcritures.provider.AccountingRecordsProviderManager;
import org.openconcerto.erp.preferences.DefaultNXProps;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
52,6 → 53,7
}
 
public int genereMouvement() throws Exception {
boolean genEcrDisabled = DefaultNXProps.getInstance().getBooleanValue(GenerationMvtSaisieVenteFacture.NOT_GEN_ECRITURE, false);
 
SQLTable avoirClientTable = base.getTable("AVOIR_CLIENT");
 
120,7 → 122,9
this.putValue("ID_COMPTE_PCE", rowCompl.getForeignID("ID_COMPTE_PCE"));
this.putValue("CREDIT", Long.valueOf(0));
this.putValue("DEBIT", Long.valueOf(taxeC));
if (!genEcrDisabled) {
ajoutEcriture();
}
taxe += taxeC;
// this.putValue("ID_COMPTE_PCE",
// rowCompl.getForeignID("ID_COMPTE_PCE_PRODUITS"));
134,10 → 138,12
this.putValue("ID_COMPTE_PCE", row.getID());
this.putValue("DEBIT", Long.valueOf(b - taxe));
this.putValue("CREDIT", Long.valueOf(0));
if (!genEcrDisabled) {
SQLRow rowEcr = ajoutEcriture();
// addAssocAnalytiqueFromProvider(rowEcr, avoirRow);
}
}
}
 
// compte TVA
Map<SQLRowAccessor, BigDecimal> tvaMap = calc.getMapHtTVA();
147,9 → 153,11
this.putValue("ID_COMPTE_PCE", rowAc.getID());
this.putValue("DEBIT", Long.valueOf(longValue));
this.putValue("CREDIT", Long.valueOf(0));
if (!genEcrDisabled) {
ajoutEcriture();
}
}
}
 
// compte Clients
int idCompteClient = avoirRow.getForeignRow("ID_CLIENT").getInt("ID_COMPTE_PCE");
164,8 → 172,9
this.putValue("DEBIT", Long.valueOf(0));
long ttc = calc.getTotalTTC().movePointRight(2).longValue();
this.putValue("CREDIT", Long.valueOf(ttc));
if (!genEcrDisabled) {
ajoutEcriture();
 
}
// Mise à jour de mouvement associé à la facture d'avoir
SQLRowValues valAvoir = new SQLRowValues(avoirClientTable);
valAvoir.put("ID_MOUVEMENT", Integer.valueOf(this.idMvt));
179,8 → 188,9
this.putValue("ID_COMPTE_PCE", Integer.valueOf(idCompteClient));
this.putValue("DEBIT", Long.valueOf(ttc));
this.putValue("CREDIT", Long.valueOf(0));
if (!genEcrDisabled) {
ajoutEcriture();
 
}
// compte Factor
int idComptefactor = rowPrefsCompte.getInt("ID_COMPTE_PCE_FACTOR");
if (idComptefactor <= 1) {
197,8 → 207,10
this.putValue("ID_COMPTE_PCE", idComptefactor);
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", Long.valueOf(ttc));
if (!genEcrDisabled) {
ajoutEcriture();
}
}
 
if (avoirRow.getInt("ID_MODE_REGLEMENT") > 1) {
new GenerationMvtReglementAvoir(avoirRow, this.idMvt);
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationReglementVenteNG.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
26,6 → 26,7
import org.openconcerto.erp.generationEcritures.provider.AccountingRecordsProvider;
import org.openconcerto.erp.generationEcritures.provider.AccountingRecordsProviderManager;
import org.openconcerto.erp.model.PrixTTC;
import org.openconcerto.erp.preferences.DefaultNXProps;
import org.openconcerto.erp.preferences.GestionCommercialeGlobalPreferencePanel;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLElement;
161,6 → 162,12
// Cheque
if (typeRegRow.getID() == TypeReglementSQLElement.CHEQUE) {
 
final SQLRowAccessor nonEmptyForeign = modeReglement.getNonEmptyForeign("ID_BANQUE");
if (nonEmptyForeign != null && nonEmptyForeign.getTable().contains("TYPE_CAISSE") && nonEmptyForeign.getBoolean("TYPE_CAISSE")) {
rowClient = null;
cptTiers = nonEmptyForeign.getForeign("ID_COMPTE_PCE");
}
 
Date dateTmp = this.date;
if (modeReglement.getObject("DATE") != null) {
dateTmp = modeReglement.getDate("DATE").getTime();
196,6 → 203,9
&& !this.rowPrefsCompte.isForeignEmpty("ID_JOURNAL_CB_ATTENTE")) {
this.putValue("ID_JOURNAL", this.rowPrefsCompte.getForeignID("ID_JOURNAL_CB_ATTENTE"));
}
if (typeRegRow.contains("ID_COMPTE_PCE_CAISSE") && (rowClient == null || rowClient.isUndefined()) && !typeRegRow.isForeignEmpty("ID_COMPTE_PCE_CAISSE")) {
this.putValue("ID_JOURNAL", JournalSQLElement.CAISSES);
}
 
int idCompteClient = cptTiers != null && !cptTiers.isUndefined() ? cptTiers.getID() : rowClient.getInt("ID_COMPTE_PCE");
if (avance) {
214,11 → 224,23
}
}
}
boolean genEcrDisabled = DefaultNXProps.getInstance().getBooleanValue(GenerationMvtSaisieVenteFacture.NOT_GEN_ECRITURE, false);
if (typeRegRow.contains("ID_COMPTE_PCE_CAISSE") && (rowClient == null || rowClient.isUndefined()) && !typeRegRow.isForeignEmpty("ID_COMPTE_PCE_CAISSE")) {
if (!modeReglement.isForeignEmpty("ID_BANQUE")) {
rowClient = null;
final SQLRow foreign = modeReglement.getForeign("ID_BANQUE");
if (foreign.getBoolean("TYPE_CAISSE")) {
idCompteClient = foreign.getForeignID("ID_COMPTE_PCE");
}
}
}
this.putValue("ID_COMPTE_PCE", idCompteClient);
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", Long.valueOf(ttc.getLongValue()));
 
if (!genEcrDisabled) {
this.ecrClient = ajoutEcriture();
}
 
// compte de reglement, caisse, cheque, ...
if (typeRegRow.getID() == TypeReglementSQLElement.ESPECE) {
235,6 → 257,11
throw new SQLException(e);
}
}
 
if (typeRegRow.contains("ID_COMPTE_PCE_CAISSE") && (rowClient == null || rowClient.isUndefined()) && !typeRegRow.isForeignEmpty("ID_COMPTE_PCE_CAISSE")) {
this.putValue("ID_COMPTE_PCE", typeRegRow.getForeignID("ID_COMPTE_PCE_CAISSE"));
}
 
if (typeRegRow.getID() == TypeReglementSQLElement.CB && this.rowPrefsCompte.getTable().contains("ID_COMPTE_PCE_CB_ATTENTE")
&& !this.rowPrefsCompte.isForeignEmpty("ID_COMPTE_PCE_CB_ATTENTE")) {
 
243,8 → 270,9
 
this.putValue("DEBIT", Long.valueOf(ttc.getLongValue()));
this.putValue("CREDIT", Long.valueOf(0));
if (!genEcrDisabled) {
ajoutEcriture();
 
}
// FIXME remove getConf
SQLRow rowSoc = ComptaPropsConfiguration.getInstanceCompta().getRowSociete();
if (rowSoc.getTable().contains("TVA_ENCAISSEMENT") && rowSoc.getBoolean("TVA_ENCAISSEMENT")) {
259,12 → 287,16
this.putValue("ID_COMPTE_PCE", rowCompteTvaCol.getID());
this.putValue("DEBIT", Long.valueOf(tva));
this.putValue("CREDIT", Long.valueOf(0));
if (!genEcrDisabled) {
ajoutEcriture();
}
 
this.putValue("ID_COMPTE_PCE", rowCompteTvaEnc.getID());
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", Long.valueOf(tva));
if (!genEcrDisabled) {
ajoutEcriture();
}
 
}
}
294,10 → 326,11
this.idMvt = getNewMouvement("ECHEANCE_CLIENT", 1, mvtSource.getID(), mvtSource.getInt("ID_PIECE"));
valEcheance.put("ID_MOUVEMENT", Integer.valueOf(this.idMvt));
valEcheance.put("DATE", dateEch);
valEcheance.put("RG", modeReglement.getBoolean("RG"));
valEcheance.put("MONTANT", Long.valueOf(ttc.getLongValue()));
valEcheance.put("ID_CLIENT", rowClient == null ? null : rowClient.getID());
valEcheance.put("TIERS", tiers);
valEcheance.put("ID_COMPTE_PCE_TIERS", cptTiers == null || !cptTiers.isUndefined() ? null : cptTiers.getID());
valEcheance.put("ID_COMPTE_PCE_TIERS", cptTiers == null || cptTiers.isUndefined() ? mvtSource.getTable().getTable("COMPTE_PCE").getUndefinedIDNumber() : cptTiers.getID());
if (source.getTable().equals(tableSaisieVenteFacture)) {
valEcheance.put("ID_SAISIE_VENTE_FACTURE", source.getID());
}
370,6 → 403,9
}
 
public void doLettrageAuto(final SQLRowAccessor source, Date dateLettrage) {
 
if (this.ecrClient != null) {
 
// A. On lettre les critures client (facture ET reglement)
// A1. Recherche criture client de facturation
 
421,6 → 457,7
e.printStackTrace();
}
}
}
 
private void paiementCheque(Date dateEch, SQLRow source, PrixTTC ttc, SQLRow rowClient, SQLRow modeRegl, SQLRow mvtSource, boolean avance, String tiers, SQLRowAccessor cptTiers)
throws SQLException {
477,6 → 514,21
if (rowPrefsCompte.getObject("ID_JOURNAL_VALEUR_ENCAISSEMENT") != null && !rowPrefsCompte.isForeignEmpty("ID_JOURNAL_VALEUR_ENCAISSEMENT")) {
idJournal = rowPrefsCompte.getForeignID("ID_JOURNAL_VALEUR_ENCAISSEMENT");
}
// compte de reglement, caisse, cheque, ...
int idCompteRegl = rowPrefsCompte.getInt("ID_COMPTE_PCE_VALEUR_ENCAISSEMENT");
if (idCompteRegl <= 1) {
idCompteRegl = ComptePCESQLElement.getIdComptePceDefault("ValeurEncaissement");
}
if (modeRegl != null) {
final SQLRowAccessor nonEmptyForeign = modeRegl.getNonEmptyForeign("ID_BANQUE");
if (nonEmptyForeign != null && nonEmptyForeign.getTable().contains("TYPE_CAISSE") && nonEmptyForeign.getBoolean("TYPE_CAISSE")) {
final SQLRow rowTypeREgl = tableMouvement.getTable("TYPE_REGLEMENT").getRow(TypeReglementSQLElement.CHEQUE);
if (rowTypeREgl.contains("ID_COMPTE_PCE_CAISSE") && (rowClient == null || rowClient.isUndefined()) && !rowTypeREgl.isForeignEmpty("ID_COMPTE_PCE_CAISSE")) {
idCompteRegl = rowTypeREgl.getForeignID("ID_COMPTE_PCE_CAISSE");
idJournal = JournalSQLElement.CAISSES;
}
}
}
 
this.putValue("ID_JOURNAL", idJournal);
this.putValue("ID_COMPTE_PCE", idCompteClient);
483,13 → 535,10
this.putValue("DEBIT", Long.valueOf(0));
this.putValue("CREDIT", Long.valueOf(ttc.getLongValue()));
 
boolean genEcrDisabled = DefaultNXProps.getInstance().getBooleanValue(GenerationMvtSaisieVenteFacture.NOT_GEN_ECRITURE, false);
if (!genEcrDisabled) {
this.ecrClient = ajoutEcriture();
 
// compte de reglement, caisse, cheque, ...
int idCompteRegl = rowPrefsCompte.getInt("ID_COMPTE_PCE_VALEUR_ENCAISSEMENT");
if (idCompteRegl <= 1) {
idCompteRegl = ComptePCESQLElement.getIdComptePceDefault("ValeurEncaissement");
}
this.putValue("ID_COMPTE_PCE", Integer.valueOf(idCompteRegl));
this.putValue("DEBIT", Long.valueOf(ttc.getLongValue()));
this.putValue("CREDIT", Long.valueOf(0));
496,6 → 545,7
 
ajoutEcriture();
}
}
 
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtReglementAchat.java
33,7 → 33,7
import java.util.Map;
 
// FIXME mettre toute les generations dans des threads à part
public final class GenerationMvtReglementAchat extends GenerationEcritures implements Runnable {
public final class GenerationMvtReglementAchat extends GenerationEcritures {
 
private int idSaisieAchat;
 
45,11 → 45,11
private static final SQLRow rowPrefsCompte = tablePrefCompte.getRow(2);
private int idPere = 1; // Id du mouvement pere
 
public GenerationMvtReglementAchat(SQLRow rowAchat, int idMvt) {
public GenerationMvtReglementAchat(SQLRow rowAchat, int idMvt) throws Exception {
setRowAnalytiqueSource(rowAchat);
this.idSaisieAchat = rowAchat.getID();
this.idPere = idMvt;
new Thread(GenerationMvtReglementAchat.this).start();
genereReglement();
}
 
private void genereReglement() throws Exception {
234,12 → 234,4
 
}
 
public void run() {
try {
genereReglement();
} catch (Exception e) {
ExceptionHandler.handle("Erreur pendant la générations des écritures comptables", e);
e.printStackTrace();
}
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtFactureFournisseur.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
22,14 → 22,14
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.utils.ExceptionHandler;
 
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.sql.SQLException;
import java.util.Date;
import java.util.Map;
 
public class GenerationMvtFactureFournisseur extends GenerationEcritures implements Runnable {
public class GenerationMvtFactureFournisseur extends GenerationEcritures {
 
public static final String ID = "accounting.records.supplychain.order";
 
42,18 → 42,18
private static final SQLTable tableMvt = base.getTable("MOUVEMENT");
private static final SQLRow rowPrefsCompte = tablePrefCompte.getRow(2);
 
public GenerationMvtFactureFournisseur(SQLRow row, int idMvt) {
public GenerationMvtFactureFournisseur(SQLRow row, int idMvt) throws SQLException {
setRowAnalytiqueSource(row);
this.idFacture = row.getID();
this.idMvt = idMvt;
(new Thread(GenerationMvtFactureFournisseur.this)).start();
genereMouvement();
}
 
public GenerationMvtFactureFournisseur(SQLRow row) {
public GenerationMvtFactureFournisseur(SQLRow row) throws SQLException {
this(row, 1);
}
 
public void genereMouvement() throws Exception {
public void genereMouvement() throws SQLException {
 
SQLRow saisieRow = getRowAnalytiqueSource();
// SQLRow taxeRow = base.getTable("TAXE").getRow(saisieRow.getInt("ID_TAXE"));
203,11 → 203,4
 
}
 
public void run() {
try {
genereMouvement();
} catch (Exception e) {
ExceptionHandler.handle("Erreur pendant la générations des écritures comptables", e);
}
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationEcritures/GenerationMvtDepotChequeClient.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
28,6 → 28,9
 
import org.openconcerto.erp.core.common.element.BanqueSQLElement;
import org.openconcerto.erp.core.finance.accounting.element.ComptePCESQLElement;
import org.openconcerto.erp.core.finance.accounting.element.JournalSQLElement;
import org.openconcerto.erp.core.finance.payment.element.TypeReglementSQLElement;
import org.openconcerto.erp.preferences.DefaultNXProps;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
90,7 → 93,21
int idJrnl = this.banque.getForeignID("ID_JOURNAL");
this.putValue("ID_JOURNAL", idJrnl);
}
if (!depot.isForeignEmpty("ID_" + BanqueSQLElement.TABLENAME)) {
SQLRow rowBanque = depot.getForeignRow("ID_" + BanqueSQLElement.TABLENAME);
if (rowBanque.getTable().contains("TYPE_CAISSE") && rowBanque.getBoolean("TYPE_CAISSE")) {
final SQLRow row = rowBanque.getTable().getTable("TYPE_REGLEMENT").getRow(TypeReglementSQLElement.CHEQUE);
if (row.getTable().contains("ID_COMPTE_PCE_CAISSE")) {
Number n = row.getNonEmptyForeignIDNumber("ID_COMPTE_PCE_CAISSE");
if (n != null) {
this.putValue("ID_JOURNAL", JournalSQLElement.CAISSES);
}
}
}
}
 
boolean genEcrDisabled = DefaultNXProps.getInstance().getBooleanValue(GenerationMvtSaisieVenteFacture.NOT_GEN_ECRITURE, false);
 
List<Integer> pieceIDs = new ArrayList<Integer>();
SQLRowValues rowValsDepotElt = new SQLRowValues(depot.getTable().getTable("DEPOT_CHEQUE_ELEMENT"));
rowValsDepotElt.putNulls("MONTANT", "TIERS", "PIECE");
131,20 → 148,36
this.putValue("ID_COMPTE_PCE", new Integer(idCompteClient));
this.putValue("DEBIT", new Long(0));
this.putValue("CREDIT", new Long(sqlRowAccessor.getLong("MONTANT")));
if (!genEcrDisabled) {
SQLRow insertedRow = ajoutEcriture();
 
sqlRowAccessor.createEmptyUpdateRow().put("ID_ECRITURE", insertedRow.getID()).getGraph().store(StoreMode.COMMIT, false);
}
sqlRowAccessor.getForeign("ID_CHEQUE_A_ENCAISSER").createEmptyUpdateRow().put("ENCAISSE", Boolean.TRUE).getGraph().store(StoreMode.COMMIT, false);
}
// compte de reglement cheque, ...
fillCompteBanqueFromRow(depot, "VenteCheque", false);
if (!depot.isForeignEmpty("ID_" + BanqueSQLElement.TABLENAME)) {
SQLRow rowBanque = depot.getForeignRow("ID_" + BanqueSQLElement.TABLENAME);
if (rowBanque.getTable().contains("TYPE_CAISSE") && rowBanque.getBoolean("TYPE_CAISSE")) {
final SQLRow row = rowBanque.getTable().getTable("TYPE_REGLEMENT").getRow(TypeReglementSQLElement.CHEQUE);
if (row.getTable().contains("ID_COMPTE_PCE_CAISSE")) {
Number n = row.getNonEmptyForeignIDNumber("ID_COMPTE_PCE_CAISSE");
if (n != null) {
this.putValue("ID_COMPTE_PCE", n);
}
}
}
}
 
this.putValue("NOM", this.nom);
this.putValue("DEBIT", new Long(this.montant));
this.putValue("CREDIT", new Long(0));
if (!genEcrDisabled) {
SQLRow insertedRow = ajoutEcriture();
 
depot.createEmptyUpdateRow().put("ID_MOUVEMENT", idMvt).put("ID_ECRITURE", insertedRow.getID()).getGraph().store(StoreMode.COMMIT, false);
 
} else {
depot.createEmptyUpdateRow().put("ID_MOUVEMENT", idMvt).getGraph().store(StoreMode.COMMIT, false);
}
pieceIDs.add(mouvementTable.getRow(idMvt).getForeignID("ID_PIECE"));
lettrageAuto(pieceIDs, this.date);
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/SpreadSheetGenerator.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
29,6 → 29,7
 
import java.awt.Point;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
56,7 → 57,7
private String printer;
private boolean exportPDF;
private Map mapReplaceText;
private String fODSP = null;
private InputStream fODSP = null;
 
protected static final String defaultLocationTemplate = "/Configuration/Template/Default/";
 
77,15 → 78,17
 
// on parcourt chaque ligne de la feuille pour recuperer les styles
int columnCount = (colEnd == -1) ? sheet.getColumnCount() : (colEnd + 1);
System.err.println("End column search : " + columnCount);
int endColumnSearch = Math.min(100, columnCount);
System.err.println("End column search : " + endColumnSearch);
 
int rowCount = (rowEnd > 0) ? rowEnd : sheet.getRowCount();
for (int i = 0; i < rowCount; i++) {
int endRowSearch = Math.min(100, rowCount);
for (int i = 0; i < endRowSearch; i++) {
int x = 0;
Map<Integer, String> mapCellStyle = new HashMap<Integer, String>();
String style = "";
 
for (int j = 0; j < columnCount; j++) {
for (int j = 0; j < endColumnSearch; j++) {
 
if (sheet.isCellValid(j, i)) {
 
183,11 → 186,14
}
 
protected SpreadSheet loadTemplate() throws IOException {
InputStream f = getStreamStatic(modelDir + File.separator + this.modele);
fODSP = modelDir + File.separator + this.modele + "p";
 
InputStream f = TemplateManager.getInstance().getTemplate(modele.replaceAll(".ods", ""));
if (f == null) {
f = getStreamStatic(modelDir + File.separator + this.modele);
fODSP = getStreamStatic(modelDir + File.separator + this.modele + "p");
if (f == null) {
f = getStreamStatic(defaultLocationTemplate + File.separator + this.modele);
fODSP = defaultLocationTemplate + File.separator + this.modele + "p";
fODSP = getStreamStatic(defaultLocationTemplate + File.separator + this.modele + "p");
if (f == null) {
ExceptionHandler.handle("Modele " + this.modele + " introuvable. Impossible de générer le document.");
System.err.println("Modele introuvable : " + (defaultLocationTemplate + File.separator + this.modele));
195,6 → 201,10
return null;
}
}
} else {
fODSP = TemplateManager.getInstance().getTemplatePrintConfiguration(modele.replaceAll(".ods", ""), null, null);
}
 
final SpreadSheet res = new ODPackage(f).getSpreadSheet();
f.close();
return res;
217,13 → 227,12
fTmp.renameTo(fDest);
 
fDest = new File(this.destDirOO, this.destFileName + ".ods");
try (final InputStream stream = getStreamStatic(fODSP)) {
if (stream != null) {
if (this.fODSP != null) {
// Copie de l'odsp
File odspOut = new File(this.destDirOO, this.destFileName + ".odsp");
StreamUtils.copy(stream, odspOut);
StreamUtils.copy(this.fODSP, odspOut);
}
}
 
try {
ssheet.saveAs(fDest);
} catch (FileNotFoundException e) {
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/OOXMLElement.java
133,6 → 133,15
if (brk != null && brk.trim().length() > 0) {
res = (res == null ? res : res.toString().replaceAll(brk, "\n"));
}
 
String attributeValueMaxChar = this.elt.getAttributeValue("maxChar");
if (attributeValueMaxChar != null) {
int maxChar = Integer.valueOf(attributeValueMaxChar);
if (res != null && res.toString().length() > maxChar) {
res = res.toString().substring(0, maxChar);
}
}
 
return res;
}
 
141,6 → 150,7
sel.addSelect(field, function);
Where w = new Where(field.getTable().getField("ID_" + this.row.getTable().getName()), "=", this.row.getID());
sel.setWhere(w);
 
return Configuration.getInstance().getBase().getDataSource().executeScalar(sel.asString());
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/RestantAReglerProvider.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
35,18 → 35,18
public RestantAReglerProvider(TypeRestantAReglerProvider t) {
this.type = t;
if (this.type == TypeRestantAReglerProvider.HT) {
acompteProv = new TotalAcompteProvider(TypeTotalAcompteProvider.HT);
cmdProvider = new TotalCommandeClientProvider(TypeTotalCommandeClientProvider.HT);
this.acompteProv = new TotalAcompteProvider(TypeTotalAcompteProvider.HT, false);
this.cmdProvider = new TotalCommandeClientProvider(TypeTotalCommandeClientProvider.HT);
} else {
acompteProv = new TotalAcompteProvider(TypeTotalAcompteProvider.TTC);
cmdProvider = new TotalCommandeClientProvider(TypeTotalCommandeClientProvider.TTC);
this.acompteProv = new TotalAcompteProvider(TypeTotalAcompteProvider.TTC, false);
this.cmdProvider = new TotalCommandeClientProvider(TypeTotalCommandeClientProvider.TTC);
}
 
}
 
public Object getValue(SpreadSheetCellValueContext context) {
Object acompte = acompteProv.getValue(context);
Object cmd = cmdProvider.getValue(context);
Object acompte = this.acompteProv.getValue(context);
Object cmd = this.cmdProvider.getValue(context);
if (acompte != null && cmd != null) {
return ((BigDecimal) cmd).subtract((BigDecimal) acompte);
} else {
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/RecapLigneFactureProvider.java
New file
0,0 → 1,108
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.generationDoc.provider;
 
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueContext;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProvider;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProviderManager;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.Where;
import org.openconcerto.utils.DecimalUtils;
 
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.Calendar;
import java.util.List;
 
public class RecapLigneFactureProvider implements SpreadSheetCellValueProvider {
 
private enum TypeLineRecapFactureProvider {
HT, TTC, PERCENT;
};
 
private final TypeLineRecapFactureProvider type;
private final boolean old, withAvoir;
 
public RecapLigneFactureProvider(TypeLineRecapFactureProvider t, boolean old) {
this(t, old, false);
}
 
public RecapLigneFactureProvider(TypeLineRecapFactureProvider t, boolean old, boolean withAvoir) {
this.type = t;
this.old = old;
this.withAvoir = withAvoir;
}
 
public Object getValue(SpreadSheetCellValueContext context) {
SQLRowAccessor row = context.getRow();
final SQLRowAccessor factureOrigin = row.getNonEmptyForeign("ID_SAISIE_VENTE_FACTURE");
final Calendar date = factureOrigin.getDate("DATE");
 
final SQLRowAccessor foreignCmdItem = row.getNonEmptyForeign("ID_COMMANDE_CLIENT_ELEMENT");
if (foreignCmdItem != null && foreignCmdItem.getBigDecimal("T_PV_HT").signum() != 0) {
 
SQLRowValues rowValsFactItem2Fetch = new SQLRowValues(row.getTable());
rowValsFactItem2Fetch.putNulls("T_PV_HT", "T_PV_TTC");
 
rowValsFactItem2Fetch.putRowValues("ID_SAISIE_VENTE_FACTURE").putNulls("DATE", "ID_AVOIR_CLIENT");
 
final List<SQLRowValues> fetch = SQLRowValuesListFetcher.create(rowValsFactItem2Fetch).fetch(new Where(row.getTable().getField("ID_COMMANDE_CLIENT_ELEMENT"), "=", foreignCmdItem.getID()));
 
BigDecimal total = BigDecimal.ZERO;
BigDecimal totalTTC = BigDecimal.ZERO;
for (SQLRowAccessor sqlRowAccessor : fetch) {
final SQLRowAccessor nonEmptyForeign = sqlRowAccessor.getNonEmptyForeign("ID_SAISIE_VENTE_FACTURE");
if (nonEmptyForeign != null && (!withAvoir || (withAvoir && sqlRowAccessor.isForeignEmpty("ID_AVOIR_CLIENT")))) {
final Calendar date2 = nonEmptyForeign.getDate("DATE");
final boolean same = old && factureOrigin.getID() == nonEmptyForeign.getID();
if (same || date2.before(date) || (date2.equals(date) && nonEmptyForeign.getID() < factureOrigin.getID())) {
total = total.add(sqlRowAccessor.getBigDecimal("T_PV_HT"));
totalTTC = totalTTC.add(sqlRowAccessor.getBigDecimal("T_PV_TTC"));
}
}
}
if (this.type == TypeLineRecapFactureProvider.HT) {
return total;
} else if (this.type == TypeLineRecapFactureProvider.TTC) {
return totalTTC;
} else {
if (foreignCmdItem.getBigDecimal("T_PV_HT").signum() != 0) {
return total.divide(foreignCmdItem.getBigDecimal("T_PV_HT"), DecimalUtils.HIGH_PRECISION).movePointRight(2).setScale(2, RoundingMode.HALF_UP) + "%";
} else {
return "";
}
}
} else {
return "";
}
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.account.line.history", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.HT, false));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.ttc", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.TTC, false));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.percent", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.PERCENT, false));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.total", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.HT, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.total.ttc", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.TTC, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.total.percent", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.PERCENT, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.with.credit", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.HT, false, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.with.credit.ttc", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.TTC, false, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.with.credit.percent", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.PERCENT, false, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.with.credit.total", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.HT, true, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.with.credit.total.ttc", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.TTC, true, true));
SpreadSheetCellValueProviderManager.put("sales.account.line.history.with.credit.total.percent", new RecapLigneFactureProvider(TypeLineRecapFactureProvider.PERCENT, true, true));
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/QteLineDocProvider.java
47,16 → 47,17
}
 
final BigDecimal qteUV = sqlRowAccessor.getBigDecimal("QTE_UNITAIRE");
final BigDecimal qte = new BigDecimal(sqlRowAccessor.getInt("QTE"));
final BigDecimal qte = sqlRowAccessor.getTable().getName().equalsIgnoreCase("BON_DE_LIVRAISON_ELEMENT") ? new BigDecimal(sqlRowAccessor.getInt("QTE_LIVREE"))
: new BigDecimal(sqlRowAccessor.getInt("QTE"));
 
final BigDecimal tare;
if (sqlRowAccessor.getObject("TARE") != null) {
tare = new BigDecimal(sqlRowAccessor.getInt("NB_COLIS"));
tare = sqlRowAccessor.getBigDecimal("TARE");
} else {
tare = BigDecimal.ZERO;
}
 
BigDecimal pdsNet = nbColis.multiply(qte).multiply(qteUV);
BigDecimal pdsNet = new BigDecimal(sqlRowAccessor.getFloat("POIDS")).multiply(qte).multiply(qteUV);
if (this.type == TypePoidsDocProvider.POIDS_NET) {
return pdsNet;
} else {
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/TotalAcompteProvider.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
31,9 → 31,11
};
 
private final TypeTotalAcompteProvider type;
private boolean old;
 
public TotalAcompteProvider(TypeTotalAcompteProvider t) {
public TotalAcompteProvider(TypeTotalAcompteProvider t, boolean old) {
this.type = t;
this.old = old;
}
 
public Object getValue(SpreadSheetCellValueContext context) {
43,7 → 45,7
Collection<? extends SQLRowAccessor> rows = row.getReferentRows(row.getTable().getTable("TR_COMMANDE_CLIENT"));
long total = 0;
Set<SQLRowAccessor> facture = new HashSet<SQLRowAccessor>();
facture.add(row);
 
for (SQLRowAccessor sqlRowAccessor : rows) {
total += getPreviousAcompte(sqlRowAccessor.getForeign("ID_COMMANDE_CLIENT"), facture, c, row);
}
52,8 → 54,10
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.account.total", new TotalAcompteProvider(TypeTotalAcompteProvider.HT));
SpreadSheetCellValueProviderManager.put("sales.account.total.ttc", new TotalAcompteProvider(TypeTotalAcompteProvider.TTC));
SpreadSheetCellValueProviderManager.put("sales.account.total.cumul", new TotalAcompteProvider(TypeTotalAcompteProvider.HT, true));
SpreadSheetCellValueProviderManager.put("sales.account.total.cumul.ttc", new TotalAcompteProvider(TypeTotalAcompteProvider.TTC, true));
SpreadSheetCellValueProviderManager.put("sales.account.total", new TotalAcompteProvider(TypeTotalAcompteProvider.HT, false));
SpreadSheetCellValueProviderManager.put("sales.account.total.ttc", new TotalAcompteProvider(TypeTotalAcompteProvider.TTC, false));
}
 
public long getPreviousAcompte(SQLRowAccessor sqlRowAccessor, Set<SQLRowAccessor> alreadyAdded, Calendar c, SQLRowAccessor origin) {
65,8 → 69,9
for (SQLRowAccessor sqlRowAccessor2 : rows) {
SQLRowAccessor rowFact = sqlRowAccessor2.getForeign("ID_SAISIE_VENTE_FACTURE");
 
if (rowFact != null && !rowFact.isUndefined() && !alreadyAdded.contains(rowFact)
&& (rowFact.getDate("DATE").before(c) || (rowFact.getDate("DATE").equals(c) && rowFact.getID() < origin.getID()))) {
final boolean sameFact = rowFact.getDate("DATE").equals(c) && rowFact.getID() < origin.getID();
final boolean oldFact = rowFact.getID() == origin.getID() && this.old;
if (rowFact != null && !rowFact.isUndefined() && !alreadyAdded.contains(rowFact) && (rowFact.getDate("DATE").before(c) || sameFact || oldFact)) {
alreadyAdded.add(rowFact);
l += this.type == TypeTotalAcompteProvider.HT ? rowFact.getLong("T_HT") : rowFact.getLong("T_TTC");
}
73,5 → 78,4
}
return l;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/ResteALivrerDocProvider.java
New file
0,0 → 1,95
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.generationDoc.provider;
 
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueContext;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProvider;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProviderManager;
import org.openconcerto.sql.model.SQLRowAccessor;
 
import java.math.BigDecimal;
 
public class ResteALivrerDocProvider implements SpreadSheetCellValueProvider {
 
protected enum ResteProvider {
RESTE, LIVRE_TOTAL, RESTE_CMD, LIVRE_TOTAL_CMD
};
 
protected final ResteProvider type;
 
public ResteALivrerDocProvider(ResteProvider t) {
this.type = t;
}
 
@Override
public Object getValue(SpreadSheetCellValueContext context) {
SQLRowAccessor sqlRowAccessor = context.getRow();
return geTotalFromRow(sqlRowAccessor);
 
}
 
protected BigDecimal geTotalFromRow(SQLRowAccessor sqlRowAccessor) {
BigDecimal totalD;
BigDecimal total = sqlRowAccessor.getBigDecimal("QTE_UNITAIRE");
total = total.multiply(new BigDecimal(sqlRowAccessor.getInt("QTE")));
 
if (this.type == ResteProvider.RESTE_CMD || this.type == ResteProvider.LIVRE_TOTAL_CMD) {
totalD = new BigDecimal(sqlRowAccessor.getInt("QTE_LIVREE"));
final BigDecimal returnedValue;
if (this.type == ResteProvider.RESTE_CMD) {
returnedValue = total.subtract(totalD);
} else {
returnedValue = totalD;
}
if (!sqlRowAccessor.isForeignEmpty("ID_ARTICLE") && returnedValue.signum() > 0) {
return returnedValue;
} else {
return null;
}
} else {
 
final SQLRowAccessor nonEmptyForeignCmdItem = sqlRowAccessor.getNonEmptyForeign("ID_COMMANDE_CLIENT_ELEMENT");
if (nonEmptyForeignCmdItem == null) {
 
totalD = sqlRowAccessor.getBigDecimal("QTE_UNITAIRE");
totalD = totalD.multiply(new BigDecimal(sqlRowAccessor.getInt("QTE_LIVREE")));
 
return total.subtract(totalD);
} else {
totalD = nonEmptyForeignCmdItem.getBigDecimal("QTE_LIVREE");
}
if (this.type == ResteProvider.LIVRE_TOTAL) {
if (totalD.signum() > 0) {
return totalD;
} else {
return null;
}
} else {
BigDecimal r = total.subtract(totalD);
if (r.signum() > 0) {
return r;
} else {
return null;
}
}
}
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.qty.delivred.total", new ResteALivrerDocProvider(ResteProvider.LIVRE_TOTAL));
SpreadSheetCellValueProviderManager.put("sales.qty.delivred.remained", new ResteALivrerDocProvider(ResteProvider.RESTE));
SpreadSheetCellValueProviderManager.put("sales.qty.cmd.delivred.total", new ResteALivrerDocProvider(ResteProvider.LIVRE_TOTAL_CMD));
SpreadSheetCellValueProviderManager.put("sales.qty.cmd.delivred.remained", new ResteALivrerDocProvider(ResteProvider.RESTE_CMD));
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/RGProvider.java
New file
0,0 → 1,76
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.generationDoc.provider;
 
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueContext;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProvider;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProviderManager;
import org.openconcerto.utils.DecimalUtils;
 
import java.math.BigDecimal;
import java.math.RoundingMode;
 
public class RGProvider implements SpreadSheetCellValueProvider {
 
private enum TypeRGProvider {
HT_RESTANT(true, true), TTC_RESTANT(false, true), HT_RG(true, false), TTC_RG(false, false);
 
private final boolean restant, ht;
 
TypeRGProvider(boolean ht, boolean restant) {
this.restant = restant;
this.ht = ht;
}
 
public boolean isHt() {
return this.ht;
}
 
public boolean isRestant() {
return this.restant;
}
};
 
private final TypeRGProvider type;
 
public RGProvider(TypeRGProvider t) {
this.type = t;
}
 
public Object getValue(SpreadSheetCellValueContext context) {
final BigDecimal total;
if (this.type.isHt()) {
total = new BigDecimal(context.getRow().getLong("T_HT")).movePointLeft(2);
} else {
total = new BigDecimal(context.getRow().getLong("T_TTC")).movePointLeft(2);
}
 
final BigDecimal pourcentRG = context.getRow().getBigDecimal("POURCENT_RG");
final BigDecimal totalRG = total.multiply(pourcentRG.movePointLeft(2), DecimalUtils.HIGH_PRECISION).setScale(2, RoundingMode.HALF_UP);
if (this.type.isRestant()) {
return total.subtract(totalRG);
} else {
return totalRG;
}
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.rg.due", new RGProvider(TypeRGProvider.TTC_RG));
SpreadSheetCellValueProviderManager.put("sales.total.sub.rg", new RGProvider(TypeRGProvider.TTC_RESTANT));
 
SpreadSheetCellValueProviderManager.put("sales.rg.due.ht", new RGProvider(TypeRGProvider.HT_RG));
SpreadSheetCellValueProviderManager.put("sales.total.sub.rg.ht", new RGProvider(TypeRGProvider.HT_RESTANT));
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/LabelAccountInvoiceProvider.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
22,12 → 22,18
 
public class LabelAccountInvoiceProvider implements SpreadSheetCellValueProvider {
 
private final String label;
 
public LabelAccountInvoiceProvider(String label) {
this.label = label;
}
 
public Object getValue(SpreadSheetCellValueContext context) {
final SQLRowAccessor row = context.getRow();
final Collection<? extends SQLRowAccessor> rows = row.getReferentRows(row.getTable().getTable("TR_COMMANDE_CLIENT"));
String result;
if (row.getBoolean("PARTIAL")) {
result = "Facturation intermédiaire, commande N°";
result = this.label + ", commande N°";
} else {
result = "Solde, commande N°";
}
41,7 → 47,8
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.account.label", new LabelAccountInvoiceProvider());
SpreadSheetCellValueProviderManager.put("sales.account.label", new LabelAccountInvoiceProvider("Facturation intermédiaire"));
SpreadSheetCellValueProviderManager.put("sales.account.label.account", new LabelAccountInvoiceProvider("Facture d'acompte"));
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/BatchListProvider.java
New file
0,0 → 1,80
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.generationDoc.provider;
 
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueContext;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProviderManager;
import org.openconcerto.sql.model.SQLRowAccessor;
 
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Collection;
 
public class BatchListProvider extends UserInitialsValueProvider {
 
private final String refTable;
 
public BatchListProvider(String refTable) {
this.refTable = refTable;
}
 
@Override
public Object getValue(SpreadSheetCellValueContext context) {
final DateFormat format = new SimpleDateFormat("dd/MM/yyyy");
final SQLRowAccessor row = context.getRow();
 
final Collection<? extends SQLRowAccessor> cols = row.asRow().getReferentRows(row.getTable().getTable(this.refTable));
final StringBuilder res = new StringBuilder();
for (SQLRowAccessor sqlRowAccessor : cols) {
final Calendar dluo = sqlRowAccessor.getDate("DLUO");
final Calendar dlc = sqlRowAccessor.getDate("DLC");
final String lot = sqlRowAccessor.getString("NUMERO_LOT");
final String serie = sqlRowAccessor.getString("NUMERO_SERIE");
if (res.length() > 0) {
res.append("\n");
}
if (serie != null && serie.trim().length() > 0) {
res.append("N° Série : " + serie);
}
if (lot != null && lot.trim().length() > 0) {
if (res.length() > 0) {
res.append(", ");
}
res.append("N° Lot : " + lot);
}
if (dlc != null) {
if (res.length() > 0) {
res.append(", ");
}
res.append("DLC : " + format.format(dlc.getTime()));
}
if (dluo != null) {
if (res.length() > 0) {
res.append(", ");
}
res.append("DLUO : " + format.format(dluo.getTime()));
}
 
}
 
return res.toString();
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.batch.list", new BatchListProvider("LOT_LIVRAISON"));
SpreadSheetCellValueProviderManager.put("purchase.batch.list", new BatchListProvider("LOT_RECEPTION"));
 
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/FormatedGlobalQtyTotalProvider.java
43,10 → 43,13
this.pieceName = withPieceName;
}
 
private final BigDecimal cent = new BigDecimal(100);
 
public Object getValue(SpreadSheetCellValueContext context) {
final SQLRowAccessor row = context.getRow();
final BigDecimal pv = row.getBigDecimal("PV_HT");
if (!this.alwaysShowOnZeroQty && pv != null && pv.compareTo(BigDecimal.ZERO) == 0) {
final BigDecimal pR = row.getBigDecimal("POURCENT_REMISE");
if (!this.alwaysShowOnZeroQty && pv != null && pv.compareTo(BigDecimal.ZERO) == 0 && (pR == null || pR.compareTo(cent) != 0)) {
return null;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/TitleInvoiceProvider.java
New file
0,0 → 1,42
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.generationDoc.provider;
 
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueContext;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProvider;
import org.openconcerto.erp.generationDoc.SpreadSheetCellValueProviderManager;
import org.openconcerto.sql.model.SQLRowAccessor;
 
public class TitleInvoiceProvider implements SpreadSheetCellValueProvider {
 
public Object getValue(SpreadSheetCellValueContext context) {
final SQLRowAccessor row = context.getRow();
String result;
if (row.getBoolean("PARTIAL")) {
result = "Facture de situation";
} else {
result = "Facture de solde";
}
if (row.getBoolean("PREVISIONNELLE")) {
result += " Prévisionnelle";
}
 
return result;
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.account.title", new TitleInvoiceProvider());
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/provider/RecapFactureProvider.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
19,6 → 19,7
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.utils.GestionDevise;
 
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Collection;
import java.util.HashSet;
31,9 → 32,12
};
 
private final TypeRecapFactureProvider type;
private final boolean withDate, withAvoir;
 
public RecapFactureProvider(TypeRecapFactureProvider t) {
public RecapFactureProvider(TypeRecapFactureProvider t, boolean withDate, boolean withAvoir) {
this.type = t;
this.withDate = withDate;
this.withAvoir = withAvoir;
}
 
public Object getValue(SpreadSheetCellValueContext context) {
55,8 → 59,14
}
 
public static void register() {
SpreadSheetCellValueProviderManager.put("sales.account.history", new RecapFactureProvider(TypeRecapFactureProvider.HT));
SpreadSheetCellValueProviderManager.put("sales.account.history.ttc", new RecapFactureProvider(TypeRecapFactureProvider.TTC));
SpreadSheetCellValueProviderManager.put("sales.account.history", new RecapFactureProvider(TypeRecapFactureProvider.HT, false, false));
SpreadSheetCellValueProviderManager.put("sales.account.history.ttc", new RecapFactureProvider(TypeRecapFactureProvider.TTC, false, false));
SpreadSheetCellValueProviderManager.put("sales.account.history.withdate", new RecapFactureProvider(TypeRecapFactureProvider.HT, true, false));
SpreadSheetCellValueProviderManager.put("sales.account.history.ttc.withdate", new RecapFactureProvider(TypeRecapFactureProvider.TTC, true, false));
SpreadSheetCellValueProviderManager.put("sales.account.history.with.credit", new RecapFactureProvider(TypeRecapFactureProvider.HT, false, true));
SpreadSheetCellValueProviderManager.put("sales.account.history.with.credit.ttc", new RecapFactureProvider(TypeRecapFactureProvider.TTC, false, true));
SpreadSheetCellValueProviderManager.put("sales.account.history.with.credit.withdate", new RecapFactureProvider(TypeRecapFactureProvider.HT, true, true));
SpreadSheetCellValueProviderManager.put("sales.account.history.with.credit.ttc.withdate", new RecapFactureProvider(TypeRecapFactureProvider.TTC, true, true));
}
 
public String getPreviousAcompte(SQLRowAccessor sqlRowAccessor, Set<SQLRowAccessor> alreadyAdded, Calendar c) {
65,15 → 75,25
}
Collection<? extends SQLRowAccessor> rows = sqlRowAccessor.getReferentRows(sqlRowAccessor.getTable().getTable("TR_COMMANDE_CLIENT"));
StringBuffer result = new StringBuffer();
SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy");
for (SQLRowAccessor sqlRowAccessor2 : rows) {
SQLRowAccessor rowFact = sqlRowAccessor2.getForeign("ID_SAISIE_VENTE_FACTURE");
 
if (rowFact != null && !rowFact.isUndefined() && !alreadyAdded.contains(rowFact) && rowFact.getDate("DATE").before(c)) {
if (rowFact != null && !rowFact.isUndefined() && !alreadyAdded.contains(rowFact) && rowFact.getDate("DATE").before(c)
&& (!this.withAvoir || (this.withAvoir && rowFact.isForeignEmpty("ID_AVOIR_CLIENT")))) {
alreadyAdded.add(rowFact);
final String fieldTotal = this.type == TypeRecapFactureProvider.HT ? "T_HT" : "T_TTC";
result.append(rowFact.getString("NUMERO") + " (" + GestionDevise.currencyToString(rowFact.getLong(fieldTotal)) + "€), ");
result.append(rowFact.getString("NUMERO"));
result.append(" (");
if (this.withDate) {
result.append(format.format(rowFact.getDate("DATE").getTime()) + " ");
}
result.append(GestionDevise.currencyToString(rowFact.getLong(fieldTotal)) + "€), ");
if (this.withDate) {
result.append("\n");
}
}
}
 
return result.toString();
}
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/OOgenerationListeXML.java
166,10 → 166,11
int nbPage = fillTable(tableau, liste, sheet, mapStyle, true, style);
int firstLine = Integer.valueOf(tableau.getAttributeValue("firstLine"));
int endLine = Integer.valueOf(tableau.getAttributeValue("endLine"));
 
Object printRangeObj = sheet.getPrintRanges();
 
System.err.println("Nombre de page == " + nbPage);
if (nbPage == 1) {
if (nbPage == 1 || endLine == -1) {
fillTable(tableau, liste, sheet, mapStyle, false, style);
} else {
 
233,6 → 234,8
int currentLine = Integer.valueOf(tableau.getAttributeValue("firstLine"));
int endPageLine = Integer.valueOf(tableau.getAttributeValue("endPageLine"));
 
int endLine = Integer.valueOf(tableau.getAttributeValue("endLine"));
 
List listElts = tableau.getChildren("element");
 
Object o = null;
241,8 → 244,15
Map<String, Double> mapSousTotal = new HashMap<String, Double>();
Map<String, Double> mapTotal = new HashMap<String, Double>();
 
// agrandissement selon le nombre de ligne à insérer
if (endLine == -1) {
sheet.setRowCount(currentLine + 1);
sheet.setRowCount(currentLine + liste.size(), currentLine);
// sheet.duplicateRows(currentLine+1, liste.size(), 1);
endPageLine = currentLine + 1 + liste.size();
}
 
// on remplit chaque ligne à partir des rows recuperées
 
for (int i = 0; i < liste.size(); i++) {
Map<String, Object> mValues = liste.get(i);
// System.err.println(mValues);
402,6 → 412,15
 
private static Object resizeValue(Element elt, Object res) {
{
String digitSize = elt.getAttributeValue("digitsFormat");
if (digitSize != null) {
int size = Integer.valueOf(digitSize);
if (res != null && res.toString().length() > 0) {
res = String.format("%-" + size + "s", res).replace(' ', '0');
}
}
}
{
String attributeValueMaxChar = elt.getAttributeValue("maxChar");
if (attributeValueMaxChar != null) {
int maxChar = Integer.valueOf(attributeValueMaxChar);
439,7 → 458,6
private static Object getValueOfComposant(Element eltField, Map<String, Object> mValues) {
 
String field = eltField.getAttributeValue("name");
 
return mValues.get(field);
}
 
606,7 → 624,8
System.err.println("End column search : " + columnCount);
 
int rowCount = (rowEnd > 0) ? rowEnd : sheet.getRowCount();
 
// Limite pour éviter les breakrepeated
rowCount = Math.min(100, rowCount);
System.err.println("End row search : " + rowCount);
for (int i = 0; i < rowCount && (mapStyleDef.keySet().size() - 2) > mapStyleFounded.keySet().size(); i++) {
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/SheetXml.java
185,7 → 185,7
 
@Override
public void run(Object source) {
EmailTemplate.askTemplate(null, table.getDBRoot(), new ValueListener() {
EmailTemplate.askTemplate(null, table.getDBRoot(), table.getName(), new ValueListener() {
 
@Override
public void valueSelected(Object value) {
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/gestcomm/OptionDocProcessor.java
61,14 → 61,20
 
BigDecimal totalHT = sqlRowValues.getBigDecimal("T_PV_HT");
final BigDecimal remisePercent = sqlRowValues.getBigDecimal("POURCENT_REMISE");
if (remisePercent != null && remisePercent.signum() > 0) {
if (remisePercent != null && remisePercent.signum() > 0 && remisePercent.movePointLeft(2).compareTo(BigDecimal.ONE) != 0) {
if (BigDecimal.ONE.subtract(remisePercent.movePointLeft(2)).signum() != 0) {
totalHT = totalHT.divide(BigDecimal.ONE.subtract(remisePercent.movePointLeft(2)), org.openconcerto.utils.DecimalUtils.HIGH_PRECISION);
}
}
// On ne recalcule pas le prix unitaire si la remise est de 100% sinon le prix
// unitaire est à 0 et les provider de quantité n'affiche plus rien
if (remisePercent == null || remisePercent.movePointLeft(2).compareTo(BigDecimal.ONE) != 0) {
BigDecimal unitPrice = totalHT.divide(qte, DecimalUtils.HIGH_PRECISION);
sqlRowValues.put("PV_HT", unitPrice);
sqlRowValues.put("PRIX_METRIQUE_VT_1", unitPrice);
}
}
}
result.add(sqlRowValues);
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/OOXMLField.java
277,9 → 277,26
if (cellSize != null && cellSize.trim().length() != 0) {
result = splitStringCell(cellSize, result);
}
String attributeValueMaxChar = this.elt.getAttributeValue("maxChar");
if (attributeValueMaxChar != null) {
int maxChar = Integer.valueOf(attributeValueMaxChar);
if (result != null && result.length() > maxChar) {
result = result.substring(0, maxChar);
}
}
 
return result;
} else {
if (display == null || !display.equalsIgnoreCase("false")) {
 
String attributeValueMaxChar = this.elt.getAttributeValue("maxChar");
if (attributeValueMaxChar != null) {
int maxChar = Integer.valueOf(attributeValueMaxChar);
if (o != null && o.toString().length() > maxChar) {
o = o.toString().substring(0, maxChar);
}
}
 
if (cellSize != null && cellSize.trim().length() != 0 && o != null) {
return splitStringCell(cellSize, o.toString());
} else {
/trunk/OpenConcerto/src/org/openconcerto/erp/generationDoc/OOgenerationXML.java
208,7 → 208,7
}
 
// Sauvegarde du fichier
return saveSpreadSheet(spreadSheet, outputDirectory, expectedFileName, templateId, rowLanguage);
return saveSpreadSheet(spreadSheet, outputDirectory, expectedFileName, templateId, rowLanguage, typeTemplate);
 
} catch (final JDOMException e) {
 
991,7 → 991,7
* @throws IOException
*/
 
private static File saveSpreadSheet(SpreadSheet ssheet, File pathDest, String fileName, String templateId, SQLRow rowLanguage) throws IOException {
private static File saveSpreadSheet(SpreadSheet ssheet, File pathDest, String fileName, String templateId, SQLRow rowLanguage, String type) throws IOException {
final String langage = rowLanguage != null ? rowLanguage.getString("CHEMIN") : null;
// Test des arguments
if (ssheet == null || pathDest == null || fileName.trim().length() == 0) {
1027,7 → 1027,7
 
// Copie de l'odsp
File odspOut = new File(pathDest, fileName + ".odsp");
try (final InputStream odspIn = TemplateManager.getInstance().getTemplatePrintConfiguration(templateId, langage, null);) {
try (final InputStream odspIn = TemplateManager.getInstance().getTemplatePrintConfiguration(templateId, langage, type);) {
if (odspIn != null) {
StreamUtils.copy(odspIn, odspOut);
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/edm/Attachment.java
95,6 → 95,10
return this.mimeType.equals(MIMETYPE_FOLDER);
}
 
public boolean isURL() {
return this.mimeType.equals(MIMETYPE_URL);
}
 
public boolean isEncrypted() {
return this.encrypted;
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/edm/AttachmentPanel.java
33,8 → 33,10
import java.awt.Frame;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Toolkit;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DropTarget;
import java.awt.dnd.DropTargetDropEvent;
42,6 → 44,7
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.net.URI;
55,6 → 58,7
import java.util.List;
import java.util.Set;
 
import javax.imageio.ImageIO;
import javax.swing.BorderFactory;
import javax.swing.JButton;
import javax.swing.JLabel;
68,7 → 72,7
 
public class AttachmentPanel extends JPanel {
 
private final SQLRowAccessor rowSource;
private SQLRowAccessor rowSource;
private final Collection<SQLRowAccessor> rowSecondaires;
private List<ListDataListener> listeners = new ArrayList<>();
 
94,6 → 98,11
setFocusable(true);
}
 
public void setRowSource(SQLRowAccessor rowSource) {
this.rowSource = rowSource;
initUI();
}
 
public void addListener(ListDataListener l) {
this.listeners.add(l);
}
116,6 → 125,7
this.filePanels.clear();
this.invalidate();
this.removeAll();
if (rowSource != null) {
GridBagConstraints c = new DefaultGridBagConstraints();
 
// Recupération de la liste des fichiers
217,6 → 227,8
toolbar.add(addFileButton);
final JButton addURLButton = new JButton("Ajouter une URL");
toolbar.add(addURLButton);
final JButton copyClipboard = new JButton("Coller l'image");
toolbar.add(copyClipboard);
 
final JProgressBar progressBar = new JProgressBar(0, 100);
progressBar.setValue(100);
283,6 → 295,36
}
});
 
copyClipboard.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
 
Transferable content = Toolkit.getDefaultToolkit().getSystemClipboard().getContents(null);
if (content == null) {
System.err.println("error: nothing found in clipboard");
return;
}
if (!content.isDataFlavorSupported(DataFlavor.imageFlavor)) {
System.err.println("error: no image found in clipbaord");
return;
}
 
try {
final BufferedImage img = (BufferedImage) content.getTransferData(DataFlavor.imageFlavor);
final File tmp = File.createTempFile("Image", ".png");
ImageIO.write(img, "png", tmp);
final AttachmentUtils utils = new AttachmentUtils();
utils.uploadFile(tmp, AttachmentPanel.this.rowSource, AttachmentPanel.this.idParent);
initUI();
tmp.delete();
} catch (UnsupportedFlavorException | IOException | SQLException e1) {
ExceptionHandler.handle(AttachmentPanel.this, "Erreur lors de la récupération de l'image", e1);
}
}
 
});
 
ScrollablePanel files = new ScrollablePanel() {
@Override
public Dimension getPreferredSize() {
405,7 → 447,8
if (t.isDataFlavorSupported(DataFlavor.javaFileListFlavor)) {
@SuppressWarnings("unchecked")
List<File> fileList = (List<File>) t.getTransferData(DataFlavor.javaFileListFlavor);
// TODO faire en arriere plan, mettre une jauge à droite du bouton ajouter
// TODO faire en arriere plan, mettre une jauge à droite du bouton
// ajouter
// et mettre un bouton d'annulation
AttachmentUtils utils = new AttachmentUtils();
boolean cancelledByUser = false;
433,6 → 476,7
scroll.getViewport().setDropTarget(dt);
fireDataChanged();
}
}
 
public Set<Attachment> getSelectedAttachments() {
return this.selectedAttachments;
/trunk/OpenConcerto/src/org/openconcerto/erp/core/edm/AttachmentUtils.java
355,7 → 355,7
config.getDirectory().getElement(AttachmentSQLElement.class).archive(rowAttachment.getId());
updateAttachmentsCountFromAttachment(rowAttachment);
 
if (!rowAttachment.isFolder()) {
if (!rowAttachment.isFolder() && !rowAttachment.isURL()) {
boolean isOnCloud = config.isOnCloud();
// Delete File
String subDir = rowAttachment.getStoragePath();
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/shipment/element/BonDeLivraisonItemSQLElement.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
35,6 → 35,14
super("BON_DE_LIVRAISON_ELEMENT", "un element de bon de livraison", "éléments de bon de livraison");
}
 
@Override
protected void ffInited() {
 
super.ffInited();
// Pour empecher la suppression d'une commande liée à un bl
setAction("ID_COMMANDE_CLIENT_ELEMENT", ReferenceAction.RESTRICT);
}
 
protected List<String> getListFields() {
final List<String> l = new ArrayList<String>();
l.add("ID_BON_DE_LIVRAISON");
49,6 → 57,7
l.add("POIDS");
l.add("T_PA_HT");
l.add("T_PV_HT");
l.add("T_PV_TTC");
return l;
}
 
69,7 → 78,7
@Override
public ListMap<String, String> getShowAs() {
final ListMap<String, String> res = new ListMap<String, String>();
res.putCollection("ID_BON_DE_LIVRAISON", "NUMERO");
res.putCollection("ID_BON_DE_LIVRAISON", "NUMERO", "DATE");
return res;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/shipment/element/BonDeLivraisonSQLElement.java
14,6 → 14,7
package org.openconcerto.erp.core.sales.shipment.element;
 
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement;
import org.openconcerto.erp.core.sales.shipment.component.BonDeLivraisonSQLComponent;
import org.openconcerto.erp.preferences.DefaultNXProps;
import org.openconcerto.sql.Configuration;
39,6 → 40,7
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.RowAction;
import org.openconcerto.sql.view.list.RowAction.PredicateRowAction;
import org.openconcerto.sql.view.list.SQLTableModelSource;
import org.openconcerto.sql.view.list.action.ListEvent;
import org.openconcerto.ui.preferences.DefaultProps;
import org.openconcerto.utils.ListMap;
90,6 → 92,13
req.addToGraphToFetch("VERROU_FACTURATION");
}
 
@Override
protected void _initTableSource(SQLTableModelSource res) {
// TODO Auto-generated method stub
super._initTableSource(res);
addCommercialFilter(res, getTable().getField("ID_COMMERCIAL"));
}
 
private void updateVerrouFacture(List<SQLRowAccessor> rows, boolean state) {
UpdateBuilder builder = new UpdateBuilder(getTable());
builder.setObject("VERROU_FACTURATION", state);
130,6 → 139,7
}
l.add("NOM");
l.add("TOTAL_HT");
l.add("TOTAL_TTC");
l.add("INFOS");
return l;
}
178,8 → 188,20
build.setWhere(new Where(alias.getField("ID_" + tableRoot), items));
 
getTable().getDBSystemRoot().getDataSource().execute(build.asString().replaceAll(" SET", " c SET "));
 
// Update commande state
if (tableRoot.equalsIgnoreCase("COMMANDE_CLIENT")) {
final SQLTable tableCmd = getTable().getTable("COMMANDE_CLIENT");
AliasedTable aliasCmd = new AliasedTable(tableCmd, "c");
Where wIN = Where.inValues(aliasCmd.getKey(), items);
String req = "UPDATE " + tableCmd.getSQLName().quote() + " c SET \"ETAT_COMMANDE\"=5 WHERE " + wIN.getClause()
+ "and (\"ETAT_COMMANDE\"=1 or \"ETAT_COMMANDE\"=2 or c.\"ETAT_COMMANDE\"=3 or c.\"ETAT_COMMANDE\"=4) "
+ "and (select SUM((i.\"QTE\"*i.\"QTE_UNITAIRE\")-i.\"QTE_LIVREE\") from " + tableCmdElement.getSQLName().quote() + " i"
+ " where i.\"ID_COMMANDE_CLIENT\"=c.\"ID\" and i.\"ARCHIVE\"=0)<=0";
getTable().getDBSystemRoot().getDataSource().execute(req);
}
}
}
 
@Override
protected void archive(TreesOfSQLRows trees, boolean cutLinks) throws SQLException {
211,6 → 233,7
}
 
}
getDirectory().getElement(LotSQLElement.class).removeLotQuantiteFromBL(ids);
super.archive(trees, cutLinks);
 
updateQteLivree(devis, "DEVIS_ELEMENT", "DEVIS");
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/shipment/action/ListeDesBonsDeLivraisonAction.java
31,14 → 31,13
import org.openconcerto.sql.view.ListeAddPanel;
import org.openconcerto.sql.view.list.BaseSQLTableModelColumn;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.IListeAction.IListeEvent;
import org.openconcerto.sql.view.list.RowAction;
import org.openconcerto.sql.view.list.RowAction.PredicateRowAction;
import org.openconcerto.sql.view.list.SQLTableModelSourceOnline;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.table.PercentTableCellRenderer;
import org.openconcerto.utils.CollectionUtils;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
52,8 → 51,10
 
import javax.swing.AbstractAction;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JTabbedPane;
import javax.swing.SwingWorker;
 
public class ListeDesBonsDeLivraisonAction extends CreateListFrameAbstractAction<BonDeLivraisonSQLElement, JFrame> {
 
94,8 → 95,8
return frame;
}
 
private ListeAddPanel getPanel(final BonDeLivraisonSQLElement eltCmd, final SQLTableModelSourceOnline tableSource, final List<RowAction> allowedActions) {
final ListeAddPanel panel = new ListeAddPanel(eltCmd, new IListe(tableSource));
private ListeAddPanel getPanel(final BonDeLivraisonSQLElement eltCmd, final SQLTableModelSourceOnline tableSource, final List<RowAction> allowedActions, String variant) {
final ListeAddPanel panel = new ListeAddPanel(eltCmd, new IListe(tableSource), variant);
 
final List<SQLField> fields = new ArrayList<SQLField>(2);
fields.add(eltCmd.getTable().getField("TOTAL_HT"));
160,7 → 161,7
};
tableSource.getColumns().add(colAvancement);
colAvancement.setRenderer(new PercentTableCellRenderer());
final ListeAddPanel panel = getPanel(eltCmd, tableSource, allowedActions);
final ListeAddPanel panel = getPanel(eltCmd, tableSource, allowedActions, "alldelivery");
return panel;
}
 
168,17 → 169,21
Collection<? extends SQLRowAccessor> rows = r.getReferentRows(r.getTable().getTable("TR_BON_DE_LIVRAISON"));
long totalFact = 0;
long total = r.getLong("TOTAL_HT");
boolean hasFact = false;
for (SQLRowAccessor row : rows) {
if (!row.isForeignEmpty("ID_SAISIE_VENTE_FACTURE")) {
SQLRowAccessor rowFact = row.getForeign("ID_SAISIE_VENTE_FACTURE");
Long l = rowFact.getLong("T_HT");
totalFact += l;
hasFact = true;
}
}
if (total > 0) {
return new BigDecimal(totalFact).divide(new BigDecimal(total), DecimalUtils.HIGH_PRECISION).movePointRight(2).setScale(2, RoundingMode.HALF_UP);
} else if (hasFact) {
return BigDecimal.ONE.movePointRight(2);
} else {
return BigDecimal.ONE.movePointRight(2);
return BigDecimal.ZERO;
}
}
 
191,7 → 196,7
final SQLInjector injector = SQLInjector.getInjector(eltCmd.getTable(), eltCmd.getTable().getTable("SAISIE_VENTE_FACTURE"));
injector.setOnlyTransfered(tableSource);
 
final ListeAddPanel panel = getPanel(eltCmd, tableSource, allowedActions);
final ListeAddPanel panel = getPanel(eltCmd, tableSource, allowedActions, "invoiced");
return panel;
}
 
205,7 → 210,7
final SQLInjector injector = SQLInjector.getInjector(eltCmd.getTable(), eltCmd.getTable().getTable("SAISIE_VENTE_FACTURE"));
injector.setOnlyNotTransfered(tableSource);
 
final ListeAddPanel panel = getPanel(eltCmd, tableSource, allowedActions);
final ListeAddPanel panel = getPanel(eltCmd, tableSource, allowedActions, "waiting");
return panel;
}
 
214,7 → 219,51
*
* @param row
*/
private void transfertFactureClient(List<SQLRowValues> rows) {
TransfertBaseSQLComponent.openTransfertFrame(rows, "SAISIE_VENTE_FACTURE");
private void transfertFactureClient(List<SQLRowValues> selectedRows) {
SwingWorker<Boolean, Object> worker = new SwingWorker<Boolean, Object>() {
@Override
protected Boolean doInBackground() throws Exception {
 
boolean b = TransfertBaseSQLComponent.isAlreadyAllTransfert(selectedRows, getConf().getRootSociete().getTable("BON_DE_LIVRAISON"),
getConf().getRootSociete().getTable("SAISIE_VENTE_FACTURE"), "TOTAL_HT", "T_HT");
 
if (b) {
String label = "Attention ";
if (selectedRows.size() > 1) {
label += " les bons de livraisons ont déjà été transféré!";
} else {
label += "le bon de livraison a déjà été transféré!";
}
label += "\n Voulez vous continuer?";
 
int ans = JOptionPane.showConfirmDialog(null, label, "Transfert Bon de livraison", JOptionPane.YES_NO_OPTION);
if (ans == JOptionPane.NO_OPTION) {
return Boolean.FALSE;
}
}
 
return Boolean.TRUE;
 
}
 
@Override
protected void done() {
try {
Boolean b = get();
if (b) {
List<SQLRowValues> selRows = new ArrayList<>();
for (SQLRowValues r : selectedRows) {
selRows.add(r.createEmptyUpdateRow());
}
TransfertBaseSQLComponent.openTransfertFrame(selectedRows, "SAISIE_VENTE_FACTURE");
 
}
} catch (Exception e) {
ExceptionHandler.handle("Erreur lors du transfert des bons de livraisons!", e);
}
}
};
worker.execute();
 
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/shipment/action/ListeDesElementsBLAction.java
New file
0,0 → 1,89
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.shipment.action;
 
import org.openconcerto.erp.action.CreateIListFrameAbstractAction;
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.core.common.ui.IListFilterDatePanel;
import org.openconcerto.erp.core.common.ui.IListTotalPanel;
import org.openconcerto.erp.core.common.ui.IListTotalPanel.Type;
import org.openconcerto.erp.core.common.ui.ListeViewPanel;
import org.openconcerto.erp.core.sales.order.element.CommandeClientElementSQLElement;
import org.openconcerto.erp.core.sales.shipment.element.BonDeLivraisonItemSQLElement;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.view.IListFrame;
import org.openconcerto.sql.view.IListPanel;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.SQLTableModelColumn;
import org.openconcerto.sql.view.list.SQLTableModelSource;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.utils.Tuple2;
 
import java.awt.GridBagConstraints;
import java.util.ArrayList;
import java.util.List;
 
public class ListeDesElementsBLAction extends CreateIListFrameAbstractAction<BonDeLivraisonItemSQLElement> {
 
public ListeDesElementsBLAction(final ComptaPropsConfiguration conf) {
super(conf, BonDeLivraisonItemSQLElement.class);
}
 
@Override
protected SQLTableModelSource createTableSource() {
final SQLTableModelSource res = super.createTableSource();
res.getReq().setWhere(new Where(getElem().getTable().getField("ID_BON_DE_LIVRAISON"), ">", 1));
return res;
}
 
@Override
protected IListPanel instantiateListPanel(final SQLTableModelSource tableSource, String panelVariant) {
return new ListeViewPanel(tableSource.getElem(), new IListe(tableSource));
}
 
@Override
protected void initFrame(IListFrame frame) {
super.initFrame(frame);
final SQLElement element = getElem();
 
final IListPanel listeAddPanel = frame.getPanel();
final SQLTableModelSource tableSource = listeAddPanel.getListe().getSource();
 
List<Tuple2<? extends SQLTableModelColumn, Type>> listField = new ArrayList<Tuple2<? extends SQLTableModelColumn, Type>>();
listField.add(Tuple2.create(tableSource.getColumn(element.getTable().getField("QTE")), IListTotalPanel.Type.SOMME_QTE));
listField.add(Tuple2.create(tableSource.getColumn(element.getTable().getField("T_PA_HT")), IListTotalPanel.Type.SOMME));
listField.add(Tuple2.create(tableSource.getColumn(element.getTable().getField("T_PV_HT")), IListTotalPanel.Type.SOMME));
listField.add(Tuple2.create(tableSource.getColumn(element.getTable().getField("T_PV_TTC")), IListTotalPanel.Type.SOMME));
IListTotalPanel total = new IListTotalPanel(listeAddPanel.getListe(), listField, null, "Total");
GridBagConstraints c = new DefaultGridBagConstraints();
c.gridy = 2;
c.weightx = 0;
c.weighty = 0;
c.anchor = GridBagConstraints.EAST;
c.fill = GridBagConstraints.NONE;
listeAddPanel.add(total, c);
 
frame.setTextTitle(String.valueOf(getValue(NAME)));
frame.getPanel().getListe().setModificationAllowed(false);
frame.getPanel().setAddVisible(false);
frame.getPanel().setSearchFullMode(true);
 
// Date panel
IListFilterDatePanel datePanel = new IListFilterDatePanel(frame.getPanel().getListe(), element.getTable().getTable("BON_DE_LIVRAISON").getField("DATE"), IListFilterDatePanel.getDefaultMap());
c.gridy++;
c.anchor = GridBagConstraints.CENTER;
frame.getPanel().add(datePanel, c);
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/shipment/ui/BonDeLivraisonItemTable.java
28,12 → 28,16
import org.openconcerto.erp.core.finance.accounting.model.CurrencyConverter;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.pos.io.BarcodeReader;
import org.openconcerto.erp.core.sales.pos.ui.BarcodeListener;
import org.openconcerto.erp.core.sales.pos.io.Barcode;
import org.openconcerto.erp.core.sales.pos.io.BarcodeListener;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.erp.core.sales.product.element.UniteVenteArticleSQLElement;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement.TypeLot;
import org.openconcerto.erp.core.sales.product.ui.ArticleRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.CurrencyWithSymbolRenderer;
import org.openconcerto.erp.core.sales.product.ui.DeliveredQtyRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.DeliveryNoteQtyRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.QtyRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.QteUnitRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.QtyToDeliverRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.ReliquatRowValuesTable;
47,6 → 51,7
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowListRSH;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.UndefinedRowValuesCache;
66,10 → 71,12
import org.openconcerto.sql.view.list.SQLTextComboTableCellEditor;
import org.openconcerto.sql.view.list.ValidStateChecker;
import org.openconcerto.ui.table.XTableColumnModel;
import org.openconcerto.utils.CompareUtils;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.Tuple3;
import org.openconcerto.utils.cc.ITransformer;
import org.openconcerto.utils.checks.ValidState;
import org.openconcerto.utils.i18n.TranslationManager;
 
import java.awt.Component;
166,7 → 173,7
final SQLTableElement tableElementArticle = new SQLTableElement(e.getTable().getField("ID_ARTICLE"), true, true, true) {
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
boolean b = super.isCellEditable(vals, rowIndex, columnIndex);
boolean b = super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
if (e.getTable().contains("ID_COMMANDE_CLIENT_ELEMENT")) {
boolean noCmdElt = vals.getObject("ID_COMMANDE_CLIENT_ELEMENT") == null || vals.isForeignEmpty("ID_COMMANDE_CLIENT_ELEMENT");
return b && noCmdElt;
188,7 → 195,7
new ITextArticleWithCompletionCellEditor(e.getTable().getTable("ARTICLE"), e.getTable().getTable("ARTICLE_FOURNISSEUR"), withDeclinaison)) {
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
boolean b = super.isCellEditable(vals, rowIndex, columnIndex);
boolean b = super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
if (e.getTable().contains("ID_COMMANDE_CLIENT_ELEMENT")) {
boolean noCmdElt = vals.getObject("ID_COMMANDE_CLIENT_ELEMENT") == null || vals.isForeignEmpty("ID_COMMANDE_CLIENT_ELEMENT");
return b && noCmdElt;
204,7 → 211,7
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
 
boolean b = super.isCellEditable(vals, rowIndex, columnIndex);
boolean b = super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
if (e.getTable().contains("ID_COMMANDE_CLIENT_ELEMENT")) {
boolean noCmdElt = vals.getObject("ID_COMMANDE_CLIENT_ELEMENT") == null || vals.isForeignEmpty("ID_COMMANDE_CLIENT_ELEMENT");
return b && noCmdElt;
273,7 → 280,7
} else if (activeCalculM2 && row != null && !row.isUndefined() && row.getID() == UniteVenteArticleSQLElement.M2) {
return false;
} else {
return super.isCellEditable(vals, rowIndex, columnIndex);
return super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
}
}
 
288,7 → 295,12
};
list.add(qteU);
 
SQLTableElement uniteVente = new SQLTableElement(e.getTable().getField("ID_UNITE_VENTE"));
SQLTableElement uniteVente = new SQLTableElement(e.getTable().getField("ID_UNITE_VENTE")) {
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
return super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
}
};
list.add(uniteVente);
 
// Quantité
311,12 → 323,17
@Override
public TableCellRenderer getTableCellRenderer() {
 
return new DeliveredQtyRowValuesRenderer();
return new DeliveryNoteQtyRowValuesRenderer();
}
 
protected Object getDefaultNullValue() {
return Integer.valueOf(0);
}
 
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
return super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
}
};
list.add(tableElement_QuantiteLivree);
 
506,30 → 523,94
list.add(this.tableElementPoidsTotalLivree);
 
// Packaging
if (prefs.getBoolean(GestionArticleGlobalPreferencePanel.ITEM_PACKAGING, false)) {
if (e.getTable().contains("POIDS_COLIS_NET") && prefs.getBoolean(GestionArticleGlobalPreferencePanel.ITEM_PACKAGING, false)) {
 
SQLTableElement poidsColis = new SQLTableElement(e.getTable().getField("POIDS_COLIS_NET"), BigDecimal.class);
list.add(poidsColis);
SQLTableElement tareColis = new SQLTableElement(e.getTable().getField("TARE"), BigDecimal.class) {
@Override
public TableCellRenderer getTableCellRenderer() {
return new QteUnitRowValuesRenderer();
}
 
};
list.add(tareColis);
 
// SQLTableElement poidsColis = new
// SQLTableElement(e.getTable().getField("POIDS_COLIS_NET"), BigDecimal.class) {
// @Override
// public TableCellRenderer getTableCellRenderer() {
// return new QteUnitRowValuesRenderer();
// }
//
// };
// list.add(poidsColis);
 
SQLTableElement nbColis = new SQLTableElement(e.getTable().getField("NB_COLIS"), Integer.class);
list.add(nbColis);
 
final SQLTableElement totalPoidsColis = new SQLTableElement(e.getTable().getField("T_POIDS_COLIS_NET"), BigDecimal.class);
list.add(totalPoidsColis);
// final SQLTableElement totalPoidsColis = new
// SQLTableElement(e.getTable().getField("T_POIDS_COLIS_NET"), BigDecimal.class) {
// @Override
// public TableCellRenderer getTableCellRenderer() {
// return new QteUnitRowValuesRenderer();
// }
//
// };
// list.add(totalPoidsColis);
//
// poidsColis.addModificationListener(totalPoidsColis);
// nbColis.addModificationListener(totalPoidsColis);
// totalPoidsColis.setModifier(new CellDynamicModifier() {
// public Object computeValueFrom(final SQLRowValues row, SQLTableElement source) {
// final BigDecimal pdsColis = row.getBigDecimal("POIDS_COLIS_NET");
// final Object o3 = row.getObject("NB_COLIS");
//
// BigDecimal pdsColisTotal = BigDecimal.ZERO;
//
// if (pdsColis != null && o3 != null) {
// int nb = (Integer) o3;
// pdsColisTotal = pdsColis.multiply(new BigDecimal(nb), DecimalUtils.HIGH_PRECISION);
// }
// return pdsColisTotal.setScale(totalPoidsColis.getDecimalDigits(),
// RoundingMode.HALF_UP);
// }
// });
 
poidsColis.addModificationListener(totalPoidsColis);
nbColis.addModificationListener(totalPoidsColis);
totalPoidsColis.setModifier(new CellDynamicModifier() {
final SQLTableElement totalPoidsBrut = new SQLTableElement(e.getTable().getField("T_POIDS_BRUT"), BigDecimal.class) {
@Override
public TableCellRenderer getTableCellRenderer() {
return new QteUnitRowValuesRenderer();
}
 
};
list.add(totalPoidsBrut);
 
tareColis.addModificationListener(totalPoidsBrut);
// poidsColis.addModificationListener(totalPoidsBrut);
nbColis.addModificationListener(totalPoidsBrut);
this.tableElementPoidsTotal.addModificationListener(totalPoidsBrut);
totalPoidsBrut.setModifier(new CellDynamicModifier() {
public Object computeValueFrom(final SQLRowValues row, SQLTableElement source) {
final Object o2 = row.getObject("POIDS_COLIS_NET");
final BigDecimal tare = row.getBigDecimal("TARE");
// final int qte = row.getInt("QTE_LIVREE");
// final BigDecimal pdsColis = row.getBigDecimal("POIDS_COLIS_NET");
final Object o3 = row.getObject("NB_COLIS");
if (o2 != null && o3 != null) {
BigDecimal poids = (BigDecimal) o2;
 
BigDecimal pdsBrutTotal = BigDecimal.ZERO;
 
if (row.getObject("T_POIDS") != null) {
pdsBrutTotal = new BigDecimal(row.getFloat("T_POIDS"));
}
 
if (tare != null && o3 != null) {
int nb = (Integer) o3;
return poids.multiply(new BigDecimal(nb), DecimalUtils.HIGH_PRECISION).setScale(totalPoidsColis.getDecimalDigits(), RoundingMode.HALF_UP);
} else {
return row.getObject("T_POIDS_COLIS_NET");
pdsBrutTotal = pdsBrutTotal.add(tare.multiply(new BigDecimal(nb)));
}
// if (pdsColis != null && o3 != null) {
// int nb = (Integer) o3;
// pdsBrutTotal = pdsBrutTotal.add(pdsColis.multiply(new BigDecimal(nb),
// DecimalUtils.HIGH_PRECISION));
// }
return pdsBrutTotal.setScale(totalPoidsBrut.getDecimalDigits(), RoundingMode.HALF_UP);
}
});
 
662,7 → 743,7
this.defaultRowVals.put("NOM", "");
final RowValuesTableModel model = new RowValuesTableModel(e, list, e.getTable().getField("NOM"), false, this.defaultRowVals) {
@Override
public void commitData() {
public void commitData() throws SQLException {
int size = getRowCount();
for (int i = 0; i < size; i++) {
SQLRowValues rowVals = getRowValuesAt(i);
672,11 → 753,60
rowVals.put("PV_T_DEVISE", rowVals.getBigDecimal("PRIX_METRIQUE_VT_1").multiply(globalQty));
}
}
super.commitData(true);
commitData(true);
}
 
@Override
public void commitData(boolean useMultipleInsertUpdate) throws SQLException {
super.commitData(useMultipleInsertUpdate);
if (getSQLElement().getTable().getName().equalsIgnoreCase("BON_DE_LIVRAISON_ELEMENT")) {
getSQLElement().getDirectory().getElement(LotSQLElement.class).updateLotQuantiteFromBLItems(getCopyOfValues());
}
}
 
@Override
public List<SQLRowValues> fetchDataFromDB(SQLRowAccessor rowVals, SQLField referentField, SQLField fieldWhere, Object value) {
final SQLTable table = getSQLElement().getTable();
if (table.getName().equals("BON_DE_LIVRAISON_ELEMENT")) {
List<SQLRowValues> newRows = new ArrayList<>();
SQLRowValues rowValsBlItem = new SQLRowValues(table);
rowValsBlItem.putNulls(table.getFieldsName());
rowValsBlItem.putRowValues("ID_UNITE_VENTE").putNulls("A_LA_PIECE");
rowValsBlItem.putRowValues("ID_ARTICLE").putNulls("ID", "CODE", "NOM", "DLC_REQUIS", "DLUO_REQUIS", "NUMERO_LOT_REQUIS", "NUMERO_SERIE_REQUIS");
final SQLTable tableLotR = table.getTable("LOT_LIVRAISON");
SQLRowValues rowValsLotRecp = new SQLRowValues(tableLotR);
rowValsLotRecp.putNulls(rowValsLotRecp.getTable().getFieldsName());
rowValsLotRecp.put("ID_BON_DE_LIVRAISON_ELEMENT", rowValsBlItem);
final List<SQLRowValues> fetch = SQLRowValuesListFetcher.create(rowValsBlItem).fetch(new Where(table.getField("ID_BON_DE_LIVRAISON"), "=", rowVals.getID()));
for (SQLRowValues row2 : fetch) {
if (fieldWhere == null || CompareUtils.equals(row2.getObject(fieldWhere.getName()), value)) {
newRows.add(row2);
}
}
return newRows;
} else {
return super.fetchDataFromDB(rowVals, referentField, fieldWhere, value);
}
}
 
};
this.setModel(model);
this.table = new RowValuesTable(model, getConfigurationFile());
model.setGestionReferentActive(true);
this.table = new RowValuesTable(model, getConfigurationFile()) {
 
@Override
public synchronized ValidState getValidState() {
if (getSQLElement().getTable().getName().equalsIgnoreCase("BON_DE_LIVRAISON_ELEMENT")) {
final LotSQLElement element = getSQLElement().getDirectory().getElement(LotSQLElement.class);
ValidState lotState = element.getValidStateOfRowValuesTable(getRowValuesTable().getRowValuesTableModel(), TypeLot.LIVRAISON);
if (lotState != ValidState.getTrueInstance()) {
return lotState;
}
}
return super.getValidState();
}
 
};
ToolTipManager.sharedInstance().unregisterComponent(this.table);
ToolTipManager.sharedInstance().unregisterComponent(this.table.getTableHeader());
this.table.getClearCloneTableElement().add("ID_COMMANDE_CLIENT_ELEMENT");
1109,7 → 1239,7
}
SQLRowAccessor foreign = row.getForeign("ID_ARTICLE");
if (foreign != null && !foreign.isUndefined() && foreign.getObject("CODE") != null && foreign.getString("CODE").equals(row.getString("CODE"))) {
return foreign.getID();
return foreign/* .getID() */;
} else {
return tableArticle.getUndefinedID();
}
1209,13 → 1339,13
}
 
@Override
public void barcodeRead(String code) {
public void barcodeRead(Barcode code) {
if (((JFrame) SwingUtilities.getRoot(getRowValuesTable())).isActive()) {
final SQLSelect selArticle = new SQLSelect();
final SQLTable tableArticle = getSQLElement().getForeignElement("ID_ARTICLE").getTable();
selArticle.addSelectStar(tableArticle);
Where w = new Where(tableArticle.getField("OBSOLETE"), "=", Boolean.FALSE);
w = w.and(new Where(tableArticle.getField("CODE_BARRE"), "=", code));
w = w.and(new Where(tableArticle.getField("CODE_BARRE"), "=", code.getData()));
selArticle.setWhere(w);
List<SQLRow> l2 = SQLRowListRSH.execute(selArticle);
if (l2.size() > 0) {
1274,7 → 1404,17
this.buttons.add(buttonStock);
 
}
final JButton e2 = new JButton("Dump");
e2.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
getModel().dumpValues();
 
}
});
this.buttons.add(e2);
 
// On réécrit la configuration au cas ou les preferences aurait changé
this.table.writeState();
 
1344,4 → 1484,12
 
}
}
 
private boolean isLotLinked(SQLRowValues vals) {
if (vals.getTable().getName().equals("BON_DE_LIVRAISON_ELEMENT")) {
return !vals.getReferentRows(vals.getTable().getTable("LOT_LIVRAISON").getField("ID_BON_DE_LIVRAISON_ELEMENT")).isEmpty();
}
return false;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/shipment/component/BonDeLivraisonSQLComponent.java
13,8 → 13,6
package org.openconcerto.erp.core.sales.shipment.component;
 
import static org.openconcerto.utils.CollectionUtils.createSet;
 
import org.openconcerto.erp.core.common.component.TransfertBaseSQLComponent;
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.common.element.NumerotationAutoSQLElement;
25,6 → 23,8
import org.openconcerto.erp.core.customerrelationship.customer.ui.CategorieComptableChoiceUI;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.invoice.element.SaisieVenteFactureItemSQLElement;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement.TypeLot;
import org.openconcerto.erp.core.sales.product.model.ProductComponent;
import org.openconcerto.erp.core.sales.product.ui.ReliquatRowValuesTable;
import org.openconcerto.erp.core.sales.shipment.element.BonDeLivraisonItemSQLElement;
41,10 → 41,13
import org.openconcerto.erp.utils.TM;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.model.ConnectionHandlerNoSetup;
import org.openconcerto.sql.model.SQLBackgroundTableCache;
import org.openconcerto.sql.model.SQLDataSource;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.Where;
55,6 → 58,7
import org.openconcerto.sql.sqlobject.SQLTextCombo;
import org.openconcerto.sql.sqlobject.itemview.SimpleRowItemView;
import org.openconcerto.sql.users.UserManager;
import org.openconcerto.sql.utils.SQLUtils;
import org.openconcerto.sql.view.EditFrame;
import org.openconcerto.sql.view.list.RowValuesTable;
import org.openconcerto.sql.view.list.RowValuesTableModel;
77,9 → 81,11
import java.awt.event.ActionListener;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.io.IOException;
import java.math.BigDecimal;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
105,8 → 111,18
private PanelOOSQLComponent panelOO;
private JUniqueTextField textNumeroUnique;
private final SQLTable tableNum = getTable().getBase().getTable("NUMEROTATION_AUTO");
private final DeviseField textTotalHT = new DeviseField(6);
private final DeviseField textTotalTVA = new DeviseField(6);
private final DeviseField textTotalHT = new DeviseField(6) {
@Override
protected void textModified() {
// No event
}
};
private final DeviseField textTotalTVA = new DeviseField(6) {
@Override
protected void textModified() {
// No event
}
};
private final DeviseField textTotalTTC = new DeviseField(6);
private final JTextField textPoidsTotal = new JTextField(6);
private final JTextField textNom = new JTextField(25);
127,6 → 143,20
}
 
@Override
public synchronized ValidState getValidState() {
final ValidState validState = super.getValidState();
if (validState.isValid()) {
final LotSQLElement element = getDirectory().getElement(LotSQLElement.class);
ValidState lotState = element.getValidStateOfRowValuesTable(getRowValuesTable().getRowValuesTableModel(), TypeLot.LIVRAISON);
if (lotState != ValidState.getTrueInstance()) {
return lotState;
}
}
return validState;
 
}
 
@Override
protected SQLRowValues createDefaults() {
this.textNumeroUnique.setText(NumerotationAutoSQLElement.getNextNumero(getElement().getClass()));
this.tableBonItem.getModel().clearRows();
393,8 → 423,8
this.addView(comboContact, "ID_CONTACT");
 
// Commercial
JLabel labelCommercial = new JLabel(getLabelFor("ID_COMMERCIAL"));
labelCommercial.setHorizontalAlignment(SwingConstants.RIGHT);
JLabel labelCommercial = new JLabel(getLabelFor("ID_COMMERCIAL"), SwingConstants.RIGHT);
c.fill = GridBagConstraints.HORIZONTAL;
 
c.gridx++;
c.weightx = 0;
539,6 → 569,8
addRequiredSQLObject(comboServiPar, "SERVI_PAR");
}
}
JTextField acompteCmd = new JTextField(15);
this.addView(acompteCmd, "T_ACOMPTE");
 
if (getTable().contains("A_ATTENTION")) {
// Date livraison
945,19 → 977,7
 
@Override
public void select(SQLRowAccessor r) {
if (r == null || r.getIDNumber() == null)
super.select(r);
else {
System.err.println(r);
final SQLRowValues rVals = r.asRowValues().deepCopy();
final SQLRowValues vals = new SQLRowValues(r.getTable());
vals.load(rVals, createSet("ID_CLIENT"));
vals.setID(rVals.getID());
System.err.println("Select CLIENT");
super.select(vals);
rVals.remove("ID_CLIENT");
super.select(rVals);
}
if (this.tableBonReliquatItem != null) {
this.tableBonReliquatItem.getRowValuesTable().clear();
if (r != null) {
981,23 → 1001,34
if (tableBonReliquatItem != null) {
this.tableBonReliquatItem.updateField("ID_BON_DE_LIVRAISON_ORIGINE", getSelectedID());
}
try {
getDirectory().getElement(LotSQLElement.class).removeLotQuantiteFromBL(Arrays.asList(getSelectedID()));
} catch (SQLException e1) {
ExceptionHandler.handle("Update Batch error", e1);
}
final List<Object> cmdClientFrom = ((BonDeLivraisonSQLElement) getElement()).getSourceTrRowsFrom(getSelectedID(), "COMMANDE_CLIENT_ELEMENT", "COMMANDE_CLIENT");
final List<Object> devisFrom = ((BonDeLivraisonSQLElement) getElement()).getSourceTrRowsFrom(getSelectedID(), "DEVIS_ELEMENT", "DEVIS");
this.tableBonItem.updateField("ID_BON_DE_LIVRAISON", getSelectedID());
this.tableBonItem.createArticle(getSelectedID(), this.getElement());
try {
SQLUtils.executeAtomic(getTable().getDBSystemRoot().getDataSource(), new ConnectionHandlerNoSetup<Object, IOException>() {
@Override
public Object handle(SQLDataSource ds) throws SQLException, IOException {
((BonDeLivraisonSQLElement) getElement()).updateQteLivree(devisFrom, "DEVIS_ELEMENT", "DEVIS");
((BonDeLivraisonSQLElement) getElement()).updateQteLivree(cmdClientFrom, "COMMANDE_CLIENT_ELEMENT", "COMMANDE_CLIENT");
 
updateStock(getSelectedID());
 
return null;
}
});
// generation du document
final SQLRow row = getTable().getRow(getSelectedID());
BonLivraisonXmlSheet bSheet = new BonLivraisonXmlSheet(row);
bSheet.createDocumentAsynchronous();
bSheet.showPrintAndExportAsynchronous(this.panelOO.isVisualisationSelected(), this.panelOO.isImpressionSelected(), true, getElement(), row);
 
try {
updateStock(getSelectedID());
} catch (SQLException e) {
throw new IllegalStateException(e);
} catch (Exception e) {
ExceptionHandler.handle(this, "erreur", e);
}
 
}
1048,10 → 1079,15
}
}
} else {
final SQLRowAccessor nonEmptyForeign = r.getNonEmptyForeign("ID_" + fromTableElt);
if (nonEmptyForeign != null && nonEmptyForeign.getTable().contains("LIVRE_FORCED") && nonEmptyForeign.getBoolean("LIVRE_FORCED")) {
this.tableBonItem.getModel().putValue(0, i, "QTE_LIVREE");
} else {
this.tableBonItem.getModel().putValue(r.getObject("QTE"), i, "QTE_LIVREE");
}
}
}
}
 
public void removeZeroQtyLines() {
int count = this.tableBonItem.getModel().getRowCount() - 1;
1139,9 → 1175,10
SQLPreferences prefs = new SQLPreferences(getTable().getDBRoot());
// Check if tr from bl or cmd pour DS
boolean stockWithBL = !prefs.getBoolean(GestionArticleGlobalPreferencePanel.STOCK_FACT, true);
SQLTable tableBlItem = getTable().getTable("BON_DE_LIVRAISON_ELEMENT");
if (getTable().getForeignTable("ID_CLIENT").contains("NOTE_2018")) {
SQLRow row = getTable().getRow(id);
List<SQLRow> items = row.getReferentRows(getTable().getTable("BON_DE_LIVRAISON_ELEMENT"));
List<SQLRow> items = row.getReferentRows(tableBlItem);
for (SQLRow sqlRow : items) {
if (sqlRow.contains("ID_COMMANDE_CLIENT_ELEMENT") && !sqlRow.isForeignEmpty("ID_COMMANDE_CLIENT_ELEMENT")) {
stockWithBL = true;
1153,21 → 1190,36
if (stockWithBL) {
 
SQLRow row = getTable().getRow(id);
StockItemsUpdater stockUpdater = new StockItemsUpdater(new StockLabel() {
final SQLTable cmdItem = tableBlItem.getForeignTable("ID_COMMANDE_CLIENT_ELEMENT");
SQLRowValues rowValsItem = new SQLRowValues(tableBlItem);
rowValsItem.setAllToNull();
final List<SQLRowValues> fetchLinkedWithCmdItem = SQLRowValuesListFetcher.create(rowValsItem)
.fetch(new Where(tableBlItem.getField("ID_BON_DE_LIVRAISON"), "=", id).and(new Where(tableBlItem.getField("ID_COMMANDE_CLIENT_ELEMENT"), "!=", cmdItem.getUndefinedIDNumber())));
 
StockItemsUpdater stockUpdaterLinkedItem = new StockItemsUpdater(new StockLabel() {
@Override
public String getLabel(SQLRowAccessor rowOrigin, SQLRowAccessor rowElt) {
return getLibelleStock(rowOrigin, rowElt);
}
}, row, row.getReferentRows(getTable().getTable("BON_DE_LIVRAISON_ELEMENT")),
getTable().contains("CREATE_VIRTUAL_STOCK") && row.getBoolean("CREATE_VIRTUAL_STOCK") ? TypeStockUpdate.REAL_VIRTUAL_DELIVER : TypeStockUpdate.REAL_DELIVER);
}, row, fetchLinkedWithCmdItem, TypeStockUpdate.REAL_DELIVER);
 
if (getTable().getDBRoot().contains("RELIQUAT_BL")) {
List<SQLRow> l = row.getReferentRows(getTable().getTable("RELIQUAT_BL").getField("ID_BON_DE_LIVRAISON_ORIGINE"));
for (SQLRow sqlRow : l) {
stockUpdater.addReliquat(sqlRow.getForeign("ID_ARTICLE"), sqlRow.getInt("QTE"), sqlRow.getBigDecimal("QTE_UNITAIRE"));
stockUpdaterLinkedItem.addReliquat(sqlRow.getForeign("ID_ARTICLE"), sqlRow.getInt("QTE"), sqlRow.getBigDecimal("QTE_UNITAIRE"));
}
}
stockUpdaterLinkedItem.update();
 
final List<SQLRowValues> fetchNotLinkedWithCmdItem = SQLRowValuesListFetcher.create(rowValsItem)
.fetch(new Where(tableBlItem.getField("ID_BON_DE_LIVRAISON"), "=", id).and(new Where(tableBlItem.getField("ID_COMMANDE_CLIENT_ELEMENT"), "=", cmdItem.getUndefinedIDNumber())));
StockItemsUpdater stockUpdater = new StockItemsUpdater(new StockLabel() {
@Override
public String getLabel(SQLRowAccessor rowOrigin, SQLRowAccessor rowElt) {
return getLibelleStock(rowOrigin, rowElt);
}
}, row, fetchNotLinkedWithCmdItem, TypeStockUpdate.REAL_VIRTUAL_DELIVER);
stockUpdater.setClearMouvementStock(false);
stockUpdater.update();
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/credit/component/AvoirClientSQLComponent.java
31,6 → 31,7
import org.openconcerto.erp.core.finance.accounting.element.ComptePCESQLElement;
import org.openconcerto.erp.core.finance.accounting.element.EcritureSQLElement;
import org.openconcerto.erp.core.finance.payment.component.ModeDeReglementSQLComponent;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.credit.ui.AvoirItemTable;
import org.openconcerto.erp.core.supplychain.stock.element.StockItemsUpdater;
import org.openconcerto.erp.core.supplychain.stock.element.StockItemsUpdater.TypeStockUpdate;
37,7 → 38,6
import org.openconcerto.erp.core.supplychain.stock.element.StockLabel;
import org.openconcerto.erp.generationDoc.gestcomm.AvoirClientXmlSheet;
import org.openconcerto.erp.generationEcritures.GenerationMvtAvoirClient;
import org.openconcerto.erp.generationEcritures.GenerationMvtSaisieVenteFacture;
import org.openconcerto.erp.model.ISQLCompteSelector;
import org.openconcerto.erp.panel.PanelOOSQLComponent;
import org.openconcerto.erp.preferences.DefaultNXProps;
219,7 → 219,11
this.eltModeRegl.setEditable(InteractionMode.DISABLED);
this.eltModeRegl.setCreated(false);
 
if (getTable().contains("ID_TAXE_PORT")) {
vals.put("ID_TAXE_PORT", TaxeCache.getCache().getFirstTaxe().getID());
}
 
 
// Selection du compte de service
final SQLRow prefs = getTable().getDBRoot().getTable("PREFS_COMPTE").getTable().getRow(2);
int idCompteVenteService = prefs.getInt("ID_COMPTE_PCE_VENTE_SERVICE");
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/credit/element/AvoirClientSQLElement.java
32,15 → 32,21
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.request.ListSQLRequest;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.RowAction;
import org.openconcerto.sql.view.list.SQLTableModelSource;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.ListMap;
 
import java.awt.event.ActionEvent;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
 
import javax.swing.AbstractAction;
import javax.swing.JOptionPane;
 
import org.apache.commons.dbutils.handlers.ArrayListHandler;
 
public class AvoirClientSQLElement extends ComptaSQLConfElement {
48,7 → 54,34
public AvoirClientSQLElement() {
super("AVOIR_CLIENT", "une facture d'avoir", "factures d'avoir");
getRowActions().addAll(new MouseSheetXmlListeListener(this, AvoirClientXmlSheet.class).getRowActions());
RowAction actionRegul = new RowAction(new AbstractAction("Forcer le solde de l'avoir") {
 
public void actionPerformed(ActionEvent e) {
 
SQLRow row = IListe.get(e).fetchSelectedRow();
 
int answer = JOptionPane.showConfirmDialog(null, "Etes vous sûr de vouloir solder l'avoir ?");
if (answer == JOptionPane.YES_OPTION) {
 
SQLRowValues rowVals = row.createEmptyUpdateRow();
rowVals.put("MONTANT_SOLDE", row.getLong("MONTANT_TTC"));
rowVals.put("MONTANT_RESTANT", 0L);
rowVals.put("SOLDE", Boolean.TRUE);
try {
rowVals.commit();
} catch (SQLException e1) {
e1.printStackTrace();
}
}
}
}, false) {
@Override
public boolean enabledFor(List<SQLRowValues> selection) {
return (selection != null && selection.size() == 1);
}
};
getRowActions().add(actionRegul);
}
 
@Override
protected void setupLinks(SQLElementLinksSetup links) {
92,6 → 125,7
@Override
protected synchronized void _initTableSource(final SQLTableModelSource table) {
super._initTableSource(table);
addCommercialFilter(table, getTable().getField("ID_COMMERCIAL"));
}
 
/*
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/element/CommandeClientSQLElement.java
123,7 → 123,7
action.setPath(Arrays.asList("Etat", "Etat", "Etat"));
getRowActions().add(action);
}
 
if (prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.TRANSFERT_AUTOMATIQUE, false)) {
PredicateRowAction actionTransfertBL = new PredicateRowAction(new AbstractAction("Transfert automatique vers BL") {
 
@Override
143,6 → 143,7
}, false);
actionTransfertBL.setPredicate(IListeEvent.getNonEmptySelectionPredicate());
getRowActions().add(actionTransfertBL);
}
 
PredicateRowAction actionStock = new PredicateRowAction(new AbstractAction("Vérification des stocks") {
 
163,6 → 164,7
actionStock.setPredicate(IListeEvent.getNonEmptySelectionPredicate());
getRowActions().add(actionStock);
 
if (prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.TRANSFERT_AUTOMATIQUE, false)) {
PredicateRowAction actionFacture = new PredicateRowAction(new AbstractAction("Transfert automatique en facture") {
 
@Override
182,8 → 184,8
}, false);
actionFacture.setPredicate(IListeEvent.getNonEmptySelectionPredicate());
getRowActions().add(actionFacture);
 
}
}
 
if (prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.ACOMPTE_DEVIS, false)) {
PredicateRowAction actionClient = new PredicateRowAction(new AbstractAction("Saisir un acompte") {
361,10 → 363,51
allowedActions.add(bonAction);
allowedActions.add(factureAction);
allowedActions.add(acompteAction);
if (prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.FACTURE_PREVISIONNELLE, false)) {
RowAction acomptePrevAction = new RowAction(new AbstractAction("Créer une facture intermédiaire (prévisionnelle)") {
public void actionPerformed(ActionEvent e) {
transfertAcompteClient(IListe.get(e).getSelectedRows(), true);
}
}, false, "sales.order.create.account.prev") {
BigDecimal cent = BigDecimal.ONE.movePointRight(2);
 
@Override
public boolean enabledFor(List<SQLRowValues> selection) {
if (selection.isEmpty() || selection.size() > 1) {
return false;
} else {
BigDecimal d = getAvancement(selection.get(0));
return NumberUtils.compare(d, cent) != 0;
}
}
};
allowedActions.add(acomptePrevAction);
}
allowedActions.add(soldeAction);
if (prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.FACTURE_PREVISIONNELLE, false)) {
RowAction acomptePrevAction = new RowAction(new AbstractAction("Facturer le solde (prévisionnelle)") {
public void actionPerformed(ActionEvent e) {
transfertSoldeClient(IListe.get(e).getSelectedRows(), true);
}
}, false, "sales.order.create.account.prev") {
BigDecimal cent = BigDecimal.ONE.movePointRight(2);
 
@Override
public boolean enabledFor(List<SQLRowValues> selection) {
if (selection.isEmpty() || selection.size() > 1) {
return false;
} else {
BigDecimal d = getAvancement(selection.get(0));
return NumberUtils.compare(d, cent) != 0;
}
}
};
allowedActions.add(acomptePrevAction);
}
allowedActions.add(cmdAction);
allowedActions.add(reliquatAction);
allowedActions.addAll(mouseSheetXmlListeListener.getRowActions());
 
getRowActions().addAll(allowedActions);
}
 
593,6 → 636,13
eltMvtStock.archive(((Number) tmp[0]).intValue());
}
}
 
final SQLTable tableCmdItem = getTable().getTable("COMMANDE_CLIENT_ELEMENT");
UpdateBuilder build = new UpdateBuilder(tableCmdItem);
build.setObject("LIVRE_FORCED", Boolean.TRUE);
build.setWhere(Where.inValues(tableCmdItem.getField("ID_COMMANDE_CLIENT"), ids));
getTable().getDBSystemRoot().getDataSource().execute(build.asString());
 
} catch (SQLException e) {
ExceptionHandler.handle("Erreur lors de la suppression des mouvements de stocks", e);
}
690,6 → 740,8
// }
// });
source.init();
addCommercialFilter(source, getTable().getField("ID_COMMERCIAL"));
 
SQLPreferences prefs = SQLPreferences.getMemCached(getTable().getDBRoot());
if (prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.ORDER_PACKAGING_MANAGEMENT, true)) {
 
852,9 → 904,13
* @param row
*/
public EditFrame transfertAcompteClient(List<SQLRowValues> rows) {
return TransfertGroupSQLComponent.openTransfertFrame(rows, "SAISIE_VENTE_FACTURE", VenteFactureSituationSQLComponent.ID);
return transfertAcompteClient(rows, false);
}
 
public EditFrame transfertAcompteClient(List<SQLRowValues> rows, boolean prev) {
return TransfertGroupSQLComponent.openTransfertFrame(rows, "SAISIE_VENTE_FACTURE", (prev) ? VenteFactureSituationSQLComponent.ID_PREVISIONNELLE : VenteFactureSituationSQLComponent.ID);
}
 
/**
* Transfert en Facture
*
864,6 → 920,10
return TransfertGroupSQLComponent.openTransfertFrame(rows, "SAISIE_VENTE_FACTURE", VenteFactureSoldeSQLComponent.ID);
}
 
public EditFrame transfertSoldeClient(List<SQLRowValues> rows, boolean prev) {
return TransfertGroupSQLComponent.openTransfertFrame(rows, "SAISIE_VENTE_FACTURE", (prev) ? VenteFactureSoldeSQLComponent.ID_PREVISIONNELLE : VenteFactureSoldeSQLComponent.ID);
}
 
public BigDecimal getAvancement(SQLRowAccessor r) {
Collection<? extends SQLRowAccessor> rows = r.getReferentRows(r.getTable().getTable("TR_COMMANDE_CLIENT"));
long totalFact = 0;
894,10 → 954,12
editFrame.setVisible(true);
}
}, true, "sales.quote.clone") {
 
@Override
public boolean enabledFor(java.util.List<org.openconcerto.sql.model.SQLRowValues> selection) {
return (selection != null && selection.size() == 1);
}
 
};
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/element/CommandeClientElementSQLElement.java
25,6 → 25,8
import org.openconcerto.sql.element.SQLComponent;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.element.UISQLComponent;
import org.openconcerto.sql.model.AliasedTable;
import org.openconcerto.sql.model.SQLDataSource;
import org.openconcerto.sql.model.SQLInjector;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
38,6 → 40,7
import org.openconcerto.sql.request.UpdateBuilder;
import org.openconcerto.sql.sqlobject.ElementComboBox;
import org.openconcerto.sql.users.UserManager;
import org.openconcerto.sql.utils.SQLUtils;
import org.openconcerto.sql.view.EditFrame;
import org.openconcerto.sql.view.EditPanel.EditMode;
import org.openconcerto.sql.view.list.IListe;
45,6 → 48,7
import org.openconcerto.sql.view.list.RowAction.PredicateRowAction;
import org.openconcerto.ui.FrameUtil;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.ListMap;
 
import java.awt.event.ActionEvent;
52,6 → 56,7
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
82,7 → 87,7
public void actionPerformed(ActionEvent e) {
List<SQLRowValues> resultId = new ArrayList<>();
CommandeClientSQLElement cmdElt = (CommandeClientSQLElement) getForeignElement("ID_COMMANDE_CLIENT");
for (SQLRowValues sqlRowAccessor : IListe.get(e).getSelectedRows()) {
for (SQLRowAccessor sqlRowAccessor : IListe.get(e).getSelectedRowAccessors()) {
resultId.add(sqlRowAccessor.getForeign("ID_COMMANDE_CLIENT").asRowValues());
}
cmdElt.transfertBonLivraisonClient(resultId);
96,7 → 101,7
 
@Override
public void actionPerformed(ActionEvent e) {
SQLRowValues selectedRow = IListe.get(e).getSelectedRow();
SQLRowAccessor selectedRow = IListe.get(e).getSelectedRowAccessor();
EditFrame f = new EditFrame(getForeignElement("ID_COMMANDE_CLIENT"), EditMode.MODIFICATION);
f.getSQLComponent().select(selectedRow.getForeignID("ID_COMMANDE_CLIENT"));
FrameUtil.showPacked(f);
135,7 → 140,7
 
@Override
public void actionPerformed(ActionEvent e) {
recalculStockTh();
recalculStockTh(null);
 
}
 
148,24 → 153,52
}
 
private void updateForceLivrer(ActionEvent e, Boolean state) {
final List<SQLRowValues> selectedRows = IListe.get(e).getSelectedRows();
final List<SQLRowAccessor> selectedRows = IListe.get(e).getSelectedRowAccessors();
final Set<Integer> ids = new HashSet<Integer>();
for (SQLRowValues sqlRowValues : selectedRows) {
final Set<Integer> idsArticle = new HashSet<Integer>();
SQLDataSource ds = null;
for (SQLRowAccessor sqlRowValues : selectedRows) {
ds = sqlRowValues.getTable().getDBSystemRoot().getDataSource();
ids.add(sqlRowValues.getID());
if (sqlRowValues.getNonEmptyForeign("ID_ARTICLE") != null) {
idsArticle.add(sqlRowValues.getForeignID("ID_ARTICLE"));
}
}
try {
SQLUtils.executeAtomic(ds, new SQLUtils.SQLFactory<Object>() {
@Override
public Object create() throws SQLException {
UpdateBuilder build = new UpdateBuilder(getTable());
build.setObject("LIVRE_FORCED", state);
build.setWhere(new Where(getTable().getKey(), ids));
getTable().getDBSystemRoot().getDataSource().execute(build.asString());
IListe.get(e).getModel().updateAll();
 
if (!idsArticle.isEmpty()) {
recalculStockTh(idsArticle);
}
for (Integer i : ids) {
getTable().fireTableModified(i);
}
return null;
}
 
public void recalculStockTh() {
});
} catch (SQLException e1) {
ExceptionHandler.handle("Erreur lors du recalcul des stocks théoriques", e1);
}
}
 
public void recalculStockTh(Collection<Integer> articles) {
if (articles != null && articles.isEmpty()) {
return;
}
// RAZ des stocks TH --> TH = REEL
final SQLTable tableStock = getTable().getDBRoot().findTable("STOCK");
String req = "UPDATE " + tableStock.getSQLName().quote() + " SET " + tableStock.getField("QTE_TH").getQuotedName() + " = " + tableStock.getField("QTE_REEL").getQuotedName() + ","
String req = "UPDATE " + tableStock.getSQLName().quote() + " s SET " + tableStock.getField("QTE_TH").getQuotedName() + " = " + tableStock.getField("QTE_REEL").getQuotedName() + ","
+ tableStock.getField("QTE_RECEPT_ATTENTE").getQuotedName() + " = 0," + tableStock.getField("QTE_LIV_ATTENTE").getQuotedName() + "=0";
if (articles != null && !articles.isEmpty()) {
req += " WHERE " + tableStock.getField("ARCHIVE").getQuotedName() + "=0 AND " + Where.inValues(new AliasedTable(tableStock, "s").getField("ID_ARTICLE"), articles).getClause();
}
tableStock.getDBSystemRoot().getDataSource().execute(req);
 
{
173,6 → 206,9
final SQLTable tableCmdElt = tableStock.getTable("COMMANDE_ELEMENT");
selCmdElt.addSelectStar(tableCmdElt);
Where w = new Where(tableCmdElt.getField("RECU_FORCED"), "=", Boolean.FALSE).and(new Where(tableCmdElt.getField("RECU"), "=", Boolean.FALSE));
if (articles != null && !articles.isEmpty()) {
w = w.and(Where.inValues(tableCmdElt.getField("ID_ARTICLE"), articles));
}
w = w.and(Where.createRaw(
tableCmdElt.getField("QTE_RECUE").getQuotedName() + " < (" + tableCmdElt.getField("QTE").getQuotedName() + "*" + tableCmdElt.getField("QTE_UNITAIRE").getQuotedName() + ")",
tableCmdElt.getField("QTE_UNITAIRE"), tableCmdElt.getField("QTE"), tableCmdElt.getField("QTE_RECUE")));
202,7 → 238,9
w = w.and(Where.createRaw(
tableCmdElt.getField("QTE_LIVREE").getQuotedName() + " < (" + tableCmdElt.getField("QTE").getQuotedName() + "*" + tableCmdElt.getField("QTE_UNITAIRE").getQuotedName() + ")",
tableCmdElt.getField("QTE_UNITAIRE"), tableCmdElt.getField("QTE"), tableCmdElt.getField("QTE_LIVREE")));
 
if (articles != null && !articles.isEmpty()) {
w = w.and(Where.inValues(tableCmdElt.getField("ID_ARTICLE"), articles));
}
selCmdElt.setWhere(w);
List<SQLRow> res = SQLRowListRSH.execute(selCmdElt);
if (res != null && res.size() > 0) {
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/action/ListeDesElementsACommanderClientAction.java
85,7 → 85,7
final String quoteQte = new SQLName(input.getAlias(eltCmd.getTable()).getAlias(), "QTE").quote();
final String quoteQteU = new SQLName(input.getAlias(eltCmd.getTable()).getAlias(), "QTE_UNITAIRE").quote();
Where w = Where.createRaw(quoteQteL + " < (" + quoteQte + "*" + quoteQteU + ")", eltCmd.getTable().getField("QTE_LIVREE"), eltCmd.getTable().getField("QTE"),
eltCmd.getTable().getField("QTE_UNITAIRE"));
eltCmd.getTable().getField("QTE_UNITAIRE")).or(Where.isNull(input.getAlias(eltCmd.getTable()).getField("QTE_LIVREE")));
w = w.and(new Where(eltCmd.getTable().getField("LIVRE_FORCED"), "=", Boolean.FALSE));
input.setWhere(w);
return input;
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/action/ListeDesCommandesClientAction.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
138,7 → 138,7
@Override
public Set<FieldPath> getPaths() {
final Path p = new PathBuilder(eltCmd.getTable()).addTable("TR_COMMANDE_CLIENT").addTable("SAISIE_VENTE_FACTURE").build();
return CollectionUtils.createSet(new FieldPath(p, "T_HT"));
return CollectionUtils.createSet(new FieldPath(p, "T_HT"), new FieldPath(p, "T_TTC"), new FieldPath(p, "T_AVOIR_TTC"));
}
};
}
200,10 → 200,15
for (SQLRowAccessor row : rows) {
if (!row.isForeignEmpty("ID_SAISIE_VENTE_FACTURE")) {
SQLRowAccessor rowFact = row.getForeign("ID_SAISIE_VENTE_FACTURE");
Long l = rowFact.getLong("T_HT");
long l = rowFact.getLong("T_HT");
long ttc = rowFact.getLong("T_TTC");
long avoir = rowFact.getLong("T_AVOIR_TTC");
// Test si la facture a été annulé par un avoir
if (ttc != avoir) {
totalFact += l;
}
}
}
if (total > 0) {
return new BigDecimal(totalFact).divide(new BigDecimal(total), DecimalUtils.HIGH_PRECISION).movePointRight(2).setScale(2, RoundingMode.HALF_UP);
} else {
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/action/ListeDesCommandesClientItemsAction.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
50,7 → 50,7
@Override
protected SQLTableModelSource createTableSource() {
final SQLTableModelSource res = super.createTableSource();
res.getReq().setWhere(new Where(getElem().getTable().getField("ID_COMMANDE_CLIENT"), ">", 1));
res.getReq().putWhere("Undef", new Where(getElem().getTable().getField("ID_COMMANDE_CLIENT"), ">", 1));
return res;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/ui/ReliquatCommandeTableModel.java
28,7 → 28,7
 
public class ReliquatCommandeTableModel extends AbstractTableModel {
 
private List<String> columns = Arrays.asList("Code", "Nom", "Qté cmd", "Reliquat");
private List<String> columns = Arrays.asList("Code", "Nom", "Taille", "Couleur", "Qté cmd", "Reliquat");
 
private final List<? extends SQLRowAccessor> values;
 
39,16 → 39,10
 
@Override
public Class<?> getColumnClass(int columnIndex) {
if (columnIndex == 0) {
if (columnIndex <= 3) {
return String.class;
} else if (columnIndex == 1) {
return String.class;
} else if (columnIndex == 2) {
return BigDecimal.class;
} else {
 
return BigDecimal.class;
 
}
}
 
72,6 → 66,20
} else if (columnIndex == 1) {
return this.values.get(rowIndex).getString("NOM");
} else if (columnIndex == 2) {
SQLRowAccessor rTaille = this.values.get(rowIndex).getNonEmptyForeign("ID_ARTICLE_DECLINAISON_TAILLE");
if (rTaille != null) {
return rTaille.getString("NOM");
} else {
return "";
}
} else if (columnIndex == 3) {
SQLRowAccessor rCouleur = this.values.get(rowIndex).getNonEmptyForeign("ID_ARTICLE_DECLINAISON_COULEUR");
if (rCouleur != null) {
return rCouleur.getString("NOM");
} else {
return "";
}
} else if (columnIndex == 4) {
return this.values.get(rowIndex).getBigDecimal("QTE_UNITAIRE").multiply(new BigDecimal(this.values.get(rowIndex).getString("QTE"))).setScale(2, RoundingMode.HALF_UP);
} else {
BigDecimal qteCmd = this.values.get(rowIndex).getBigDecimal("QTE_UNITAIRE").multiply(new BigDecimal(this.values.get(rowIndex).getString("QTE"))).setScale(2, RoundingMode.HALF_UP);
95,9 → 103,13
final SQLTable table = tableCmd.getTable(tableCmd.getName() + "_ELEMENT");
SQLRowValues rowVals = new SQLRowValues(table);
final String fieldQteRecueLivree = tableCmd.getName().equals("COMMANDE") ? "QTE_RECUE" : "QTE_LIVREE";
 
rowVals.putNulls("CODE", "NOM", "QTE", "QTE_UNITAIRE", fieldQteRecueLivree);
rowVals.putRowValues("ID_ARTICLE_DECLINAISON_TAILLE").putNulls("NOM");
rowVals.putRowValues("ID_ARTICLE_DECLINAISON_COULEUR").putNulls("NOM");
 
final Where w = new Where(table.getField("ID_" + tableCmd.getName()), "=", rowCmd.getID());
final Where w = new Where(table.getField("ID_" + tableCmd.getName()), "=", rowCmd.getID())
.and(new Where(table.getField("ID_ARTICLE"), "!=", table.getForeignTable("ID_ARTICLE").getUndefinedIDNumber()));
final Where w2 = Where
.createRaw(table.getField(fieldQteRecueLivree).getQuotedName() + " < (" + table.getField("QTE").getQuotedName() + "*" + table.getField("QTE_UNITAIRE").getQuotedName() + ")",
table.getField("QTE_UNITAIRE"), table.getField("QTE"), table.getField(fieldQteRecueLivree))
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/order/component/CommandeClientSQLComponent.java
251,7 → 251,7
 
@Override
public void propertyChange(PropertyChangeEvent evt) {
if (!isFilling() && comboClient.getValue() != null) {
if ((getMode() == Mode.INSERTION || !isFilling()) && comboClient.getValue() != null) {
Integer id = comboClient.getValue();
 
if (id > 1) {
563,6 → 563,7
 
// Table d'élément
this.table = new CommandeClientItemTable();
this.table.getRowValuesTable().getRowValuesTableModel().setValidationField(getTable().getTable("BON_DE_LIVRAISON_ELEMENT").getField("ID_COMMANDE_CLIENT_ELEMENT"));
JTabbedPane pane = new JTabbedPane();
c.fill = GridBagConstraints.BOTH;
c.gridy++;
930,19 → 931,8
 
@Override
public void select(SQLRowAccessor r) {
if (r == null || r.getIDNumber() == null)
super.select(r);
else {
System.err.println(r);
final SQLRowValues rVals = r.asRowValues().deepCopy();
final SQLRowValues vals = new SQLRowValues(r.getTable());
vals.load(rVals, createSet("ID_CLIENT"));
vals.setID(rVals.getID());
System.err.println("Select CLIENT");
super.select(vals);
rVals.remove("ID_CLIENT");
super.select(rVals);
}
 
if (r != null) {
this.table.getRowValuesTable().insertFrom(r);
this.tableFacturationItem.getRowValuesTable().insertFrom(r);
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/account/PartialInvoiceEditGroup.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
36,7 → 36,8
gCustomer.addItem("ID_ADRESSE");
gCustomer.addItem("ID_ADRESSE_LIVRAISON");
gCustomer.addItem("REMISE_HT");
gCustomer.addItem("POURCENT_RG");
gCustomer.addItem("PREVISIONNELLE");
add(gCustomer);
 
final Group gElements = new Group("sales.invoice.partial.items");
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/account/VenteFactureSituationSQLComponent.java
72,6 → 72,7
 
public class VenteFactureSituationSQLComponent extends TransfertGroupSQLComponent {
public static final String ID = "sales.invoice.partial";
public static final String ID_PREVISIONNELLE = "sales.invoice.partial.future";
 
private PanelOOSQLComponent panelOO;
 
268,6 → 269,10
public JComponent createEditor(String id) {
 
if (id.equals("sales.invoice.number")) {
if (getCode().equals(ID_PREVISIONNELLE)) {
this.numberField = new JUniqueTextField(20);
return this.numberField;
} else {
this.numberField = new JUniqueTextField(20) {
@Override
public String getAutoRefreshNumber() {
279,6 → 284,7
}
};
return this.numberField;
}
} else if (id.equals("panel.oo")) {
this.panelOO = new PanelOOSQLComponent(this);
return this.panelOO;
393,8 → 399,9
}
((AbstractArticleItemTable) getEditor("sales.invoice.partial.items.list")).updateField("ID_SAISIE_VENTE_FACTURE", idSaisieVF);
 
if (!rowFacture.getBoolean("PREVISIONNELLE")) {
new GenerationMvtSaisieVenteFacture(idSaisieVF);
 
}
try {
VenteFactureXmlSheet sheet = new VenteFactureXmlSheet(rowFacture);
sheet.createDocument();
421,6 → 428,7
final SQLRow rowFacture = getTable().getRow(id);
((AbstractArticleItemTable) getEditor("sales.invoice.partial.items.list")).updateField("ID_SAISIE_VENTE_FACTURE", id);
 
if (!rowFacture.getBoolean("PREVISIONNELLE")) {
int idMvt = rowFacture.getInt("ID_MOUVEMENT");
// on supprime tout ce qui est lié à la facture
System.err.println("Archivage des fils");
427,6 → 435,7
EcritureSQLElement eltEcr = (EcritureSQLElement) getDirectory().getElement("ECRITURE");
eltEcr.archiveMouvementProfondeur(idMvt, false);
new GenerationMvtSaisieVenteFacture(id);
}
try {
VenteFactureXmlSheet sheet = new VenteFactureXmlSheet(rowFacture);
sheet.createDocument();
434,12 → 443,31
} catch (Exception e) {
ExceptionHandler.handle("Une erreur est survenue lors de la création du document.", e);
}
// incrémentation du numéro auto
if (NumerotationAutoSQLElement.getNextNumero(SaisieVenteFactureSQLElement.class, rowFacture.getDate("DATE").getTime()).equalsIgnoreCase(rowFacture.getString("NUMERO"))) {
SQLRowValues rowVals = new SQLRowValues(this.tableNum);
 
String labelNumberFor = NumerotationAutoSQLElement.getLabelNumberFor(SaisieVenteFactureSQLElement.class);
int val = this.tableNum.getRow(2).getInt(labelNumberFor);
val++;
rowVals.put(labelNumberFor, Integer.valueOf(val));
try {
rowVals.update(2);
} catch (SQLException e1) {
e1.printStackTrace();
}
}
}
 
@Override
protected SQLRowValues createDefaults() {
SQLRowValues rowVals = new SQLRowValues(getTable());
if (getCode().equals(ID_PREVISIONNELLE)) {
rowVals.put("NUMERO", "PREV_" + NumerotationAutoSQLElement.getNextNumero(SaisieVenteFactureSQLElement.class, new Date()));
rowVals.put("PREVISIONNELLE", Boolean.TRUE);
} else {
rowVals.put("NUMERO", NumerotationAutoSQLElement.getNextNumero(SaisieVenteFactureSQLElement.class, new Date()));
}
rowVals.put("PARTIAL", Boolean.TRUE);
return rowVals;
}
452,4 → 480,5
return super.addView(comp, id);
}
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/account/VenteFactureSoldeEditGroup.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
35,6 → 35,8
final Group gCustomer = new Group("sales.invoice.partial.balance.customer");
gCustomer.addItem("sales.invoice.customer", LayoutHints.DEFAULT_LARGE_FIELD_HINTS);
gCustomer.addItem("REMISE_HT");
gCustomer.addItem("POURCENT_RG");
gCustomer.addItem("PREVISIONNELLE");
add(gCustomer);
 
final Group gElements = new Group("sales.invoice.partial.balance.items");
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/account/VenteFactureSoldeSQLComponent.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
47,6 → 47,7
 
public class VenteFactureSoldeSQLComponent extends VenteFactureSituationSQLComponent {
public static final String ID = "sales.invoice.partial.balance";
public static final String ID_PREVISIONNELLE = "sales.invoice.partial.balance.future";
 
public VenteFactureSoldeSQLComponent(SQLElement element) {
super(element, (Group) GlobalMapper.getInstance().get(ID));
66,7 → 67,12
@Override
protected SQLRowValues createDefaults() {
SQLRowValues rowVals = new SQLRowValues(getTable());
if (getCode().equals(ID_PREVISIONNELLE)) {
rowVals.put("NUMERO", "PREV_" + NumerotationAutoSQLElement.getNextNumero(SaisieVenteFactureSQLElement.class, new Date()));
rowVals.put("PREVISIONNELLE", Boolean.TRUE);
} else {
rowVals.put("NUMERO", NumerotationAutoSQLElement.getNextNumero(SaisieVenteFactureSQLElement.class, new Date()));
}
rowVals.put("SOLDE", Boolean.TRUE);
return rowVals;
}
132,10 → 138,15
SQLRowAccessor rowFacture = sqlRowAccessor2.getForeign("ID_SAISIE_VENTE_FACTURE");
if (!alreadyAdded.contains(rowFacture)) {
alreadyAdded.add(rowFacture);
long ttc = rowFacture.getLong("T_TTC");
long avoir = rowFacture.getLong("T_AVOIR_TTC");
// test si facture annulée
if (ttc != avoir) {
l += rowFacture.getLong("T_HT");
}
}
}
}
return l;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/action/ListeDesFactureItemsAction.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
41,7 → 41,7
@Override
protected SQLTableModelSource createTableSource() {
final SQLTableModelSource res = super.createTableSource();
res.getReq().setWhere(new Where(getElem().getTable().getField("ID_SAISIE_VENTE_FACTURE"), ">", 1));
res.getReq().putWhere("Undef", new Where(getElem().getTable().getField("ID_SAISIE_VENTE_FACTURE"), ">", 1));
return res;
}
49,6 → 49,7
protected IListPanel instantiateListPanel(SQLTableModelSource tableSource, String panelVariant) {
return new ListeViewPanel(tableSource.getElem(), new IListe(tableSource));
}
 
@Override
protected void initFrame(IListFrame frame) {
final SQLElement element = this.getElem();
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/action/ListeDesFacturesPrevisionnellesOCAction.java
New file
0,0 → 1,146
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.invoice.action;
 
import org.openconcerto.erp.action.CreateFrameAbstractAction;
import org.openconcerto.erp.core.common.element.NumerotationAutoSQLElement;
import org.openconcerto.erp.core.sales.account.VenteFactureSituationSQLComponent;
import org.openconcerto.erp.core.sales.account.VenteFactureSoldeSQLComponent;
import org.openconcerto.erp.core.sales.invoice.element.SaisieVenteFactureSQLElement;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLComponent;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.view.EditFrame;
import org.openconcerto.sql.view.EditPanel;
import org.openconcerto.sql.view.IListFrame;
import org.openconcerto.sql.view.ListeAddPanel;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.IListeAction.IListeEvent;
import org.openconcerto.sql.view.list.RowAction.PredicateRowAction;
 
import java.awt.event.ActionEvent;
import java.util.Date;
 
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JButton;
import javax.swing.JFrame;
 
public class ListeDesFacturesPrevisionnellesOCAction extends CreateFrameAbstractAction {
 
private IListFrame listFrame;
 
public ListeDesFacturesPrevisionnellesOCAction() {
super();
this.putValue(Action.NAME, "Liste des factures prévisionnelles");
}
 
@Override
public JFrame createFrame() {
 
SQLElement eltFacture = Configuration.getInstance().getDirectory().getElement("SAISIE_VENTE_FACTURE");
 
// Filter
Where wPrev = new Where(eltFacture.getTable().getField("PREVISIONNELLE"), "=", Boolean.TRUE);
final ListeAddPanel listPanel = new ListeAddPanel(eltFacture, new IListe(eltFacture.createTableSource(wPrev))) {
 
protected void handleAction(JButton source, ActionEvent evt) {
 
SQLRow row = this.getElement().getTable().getRow(this.getListe().getSelectedId());
 
if (row != null && row.getID() > 1) {
final SQLRowAccessor mvt = row.getForeign("ID_MOUVEMENT");
if (source == this.buttonEffacer) {
 
super.handleAction(source, evt);
 
} else {
if (source == this.buttonModifier) {
 
EditFrame editModifyFrame;
if (this.element.getTable().getName().equals("SAISIE_VENTE_FACTURE") && row.getBoolean("PARTIAL")) {
editModifyFrame = new EditFrame(this.element.createComponent(VenteFactureSituationSQLComponent.ID_PREVISIONNELLE), EditPanel.MODIFICATION);
} else if (this.element.getTable().getName().equals("SAISIE_VENTE_FACTURE") && row.getBoolean("SOLDE")) {
editModifyFrame = new EditFrame(this.element.createComponent(VenteFactureSoldeSQLComponent.ID_PREVISIONNELLE), EditPanel.MODIFICATION);
} else {
editModifyFrame = new EditFrame(this.element, EditPanel.MODIFICATION);
}
editModifyFrame.selectionId(this.getListe().getSelectedId());
editModifyFrame.setVisible(true);
// Bouton delete retiré pour passer par la méthode qui supprime les
// ecritures comptables
editModifyFrame.getPanel().disableDelete();
} else {
super.handleAction(source, evt);
}
}
} else {
super.handleAction(source, evt);
}
}
};
listPanel.setAddVisible(false);
 
this.listFrame = new IListFrame(listPanel) {
@Override
public void setTitle() {
String title = "Liste des factures prévisionnelles";
 
final int rowCount = listPanel.getListe().getRowCount();
title += ", " + getPlural("ligne", rowCount);
final int total = listPanel.getListe().getTotalRowCount();
if (total != rowCount)
title += " / " + total;
 
int count = listPanel.getListe().getItemCount();
if (count >= 0)
title += ", " + this.getPlural("élément", count);
 
this.setTitle(title);
}
};
PredicateRowAction action = new PredicateRowAction(new AbstractAction("Transférer en facture") {
public void actionPerformed(ActionEvent e) {
 
SQLElement eltFacture = Configuration.getInstance().getDirectory().getElement("SAISIE_VENTE_FACTURE");
final SQLComponent comp;
SQLRowValues rowVals = IListe.get(e).fetchSelectedRow().asRowValues();
if (rowVals.getBoolean("PARTIAL")) {
comp = eltFacture.createComponent(VenteFactureSituationSQLComponent.ID);
} else if (rowVals.getBoolean("SOLDE")) {
comp = eltFacture.createComponent(VenteFactureSoldeSQLComponent.ID);
} else {
comp = eltFacture.createComponent(SQLElement.DEFAULT_COMP_ID);
}
EditFrame frameTransfert = new EditFrame(comp, EditFrame.MODIFICATION);
frameTransfert.setTitle("Transfert en facture");
rowVals.put("NUMERO", NumerotationAutoSQLElement.getNextNumero(SaisieVenteFactureSQLElement.class, new Date()));
rowVals.put("DATE", new Date());
rowVals.put("PREVISIONNELLE", Boolean.FALSE);
comp.select(rowVals);
frameTransfert.setVisible(true);
 
}
}, true);
action.setPredicate(IListeEvent.getSingleSelectionPredicate());
this.listFrame.getPanel().getListe().addIListeAction(action);
 
return this.listFrame;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/action/ListeDesElementsFactureAction.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
44,7 → 44,7
 
IListe liste = new IListe(element.getTableSource(true));
final ListeViewPanel listeAddPanel = new ListeViewPanel(element, liste);
listeAddPanel.getListe().getRequest().setWhere(new Where(element.getTable().getField("ID_SAISIE_VENTE_FACTURE"), ">", 1));
listeAddPanel.getListe().getRequest().putWhere("Undef",new Where(element.getTable().getField("ID_SAISIE_VENTE_FACTURE"), ">", 1));
List<SQLField> l = new ArrayList<SQLField>();
l.add(element.getTable().getField("T_PV_HT"));
l.add(element.getTable().getField("T_PV_TTC"));
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/ui/ListeDesVentesPanel.java
16,13 → 16,17
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.core.common.ui.IListFilterDatePanel;
import org.openconcerto.erp.core.common.ui.IListTotalPanel;
import org.openconcerto.erp.core.common.ui.IListTotalPanel.Type;
import org.openconcerto.erp.core.common.ui.ListeViewPanel;
import org.openconcerto.erp.core.finance.accounting.ui.ListeGestCommEltPanel;
import org.openconcerto.erp.core.sales.account.VenteFactureSituationSQLComponent;
import org.openconcerto.erp.core.sales.account.VenteFactureSoldeSQLComponent;
import org.openconcerto.erp.core.sales.invoice.element.SaisieVenteFactureSQLElement;
import org.openconcerto.erp.core.sales.pos.POSConfiguration;
import org.openconcerto.erp.core.sales.pos.element.TicketCaisseSQLElement;
import org.openconcerto.erp.core.sales.pos.model.ArticleCache;
import org.openconcerto.erp.core.sales.pos.ui.TextAreaTicketPanel;
import org.openconcerto.sql.TM;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.element.SQLElementDirectory;
import org.openconcerto.sql.model.FieldPath;
31,6 → 35,9
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.model.graph.Path;
import org.openconcerto.sql.view.EditFrame;
import org.openconcerto.sql.view.EditPanel;
import org.openconcerto.sql.view.list.BaseSQLTableModelColumn;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.IListeAction.IListeEvent;
import org.openconcerto.sql.view.list.ITableModel;
41,8 → 48,10
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.JLabelBold;
import org.openconcerto.ui.PanelFrame;
import org.openconcerto.utils.CollectionUtils;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.TableSorter;
import org.openconcerto.utils.Tuple2;
import org.openconcerto.utils.cc.IClosure;
 
import java.awt.GridBagConstraints;
49,11 → 58,13
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.event.ActionEvent;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Set;
 
import javax.swing.AbstractAction;
import javax.swing.JButton;
94,7 → 105,7
if (src.getReq().getWhere() != null) {
wPrev = wPrev.and(src.getReq().getWhere());
}
src.getReq().setWhere(wPrev);
src.getReq().putWhere("Previsionnelle", wPrev);
 
final ListeFactureRenderer rend = new ListeFactureRenderer();
for (SQLTableModelColumn column : src.getColumns()) {
144,10 → 155,53
 
this.listeFact.setOpaque(false);
this.listeFact.getListe().setModificationAllowed(true);
final PredicateRowAction action = new PredicateRowAction(new AbstractAction(TM.tr("display")) {
 
@Override
public void actionPerformed(ActionEvent e) {
EditFrame editModifyFrame;
SQLRowAccessor row = IListe.get(e).getSelectedRowAccessor();
if (eltFacture.getTable().getName().equals("SAISIE_VENTE_FACTURE") && row.getBoolean("PARTIAL")) {
editModifyFrame = new EditFrame(eltFacture.createComponent(VenteFactureSituationSQLComponent.ID), EditPanel.READONLY);
} else if (eltFacture.getTable().getName().equals("SAISIE_VENTE_FACTURE") && row.getBoolean("SOLDE")) {
editModifyFrame = new EditFrame(eltFacture.createComponent(VenteFactureSoldeSQLComponent.ID), EditPanel.READONLY);
} else {
editModifyFrame = new EditFrame(eltFacture, EditPanel.READONLY);
}
editModifyFrame.selectionId(row.getID());
editModifyFrame.setVisible(true);
 
}
}, false);
action.setPredicate(IListeEvent.getSingleSelectionPredicate());
this.listeFact.getListe().setDefaultRowAction(action);
 
final JTable tableFact = this.listeFact.getListe().getJTable();
final SQLTableModelColumn numeroCol = src.getColumn(eltFacture.getTable().getField("NUMERO"));
((TableSorter) tableFact.getModel()).setSortingStatus(src.getColumns().indexOf(numeroCol), TableSorter.ASCENDING);
 
BaseSQLTableModelColumn totalAvoirHT = new BaseSQLTableModelColumn("Fact. - Avoir HT", BigDecimal.class) {
 
@Override
protected Object show_(SQLRowAccessor r) {
BigDecimal bF = new BigDecimal(r.getLong("T_HT")).movePointLeft(2);
if (!r.isForeignEmpty("ID_AVOIR_CLIENT")) {
BigDecimal b = new BigDecimal(r.getForeign("ID_AVOIR_CLIENT").getLong("MONTANT_HT")).movePointLeft(2);
return bF.subtract(b);
}
return bF;
}
 
@Override
public Set<FieldPath> getPaths() {
Path p = new Path(eltFacture.getTable());
p = p.add(eltFacture.getTable().getField("ID_AVOIR_CLIENT"));
 
return CollectionUtils.createSet(new FieldPath(p, "MONTANT_HT"));
}
};
src.getColumns().add(src.getColumns().indexOf(src.getColumn(eltFacture.getTable().getField("T_HT"))), totalAvoirHT);
 
JPanel panelFacture = new JPanel(new GridBagLayout());
GridBagConstraints cFacture = new DefaultGridBagConstraints();
 
159,13 → 213,14
cFacture.fill = GridBagConstraints.BOTH;
panelFacture.add(this.listeFact, cFacture);
 
List<SQLField> l = new ArrayList<SQLField>();
List<Tuple2<? extends SQLTableModelColumn, Type>> l = new ArrayList<Tuple2<? extends SQLTableModelColumn, Type>>();
if (this.listeFact.getListe().getSource().getColumn(eltFacture.getTable().getField("T_HA")) != null) {
l.add(eltFacture.getTable().getField("T_HA"));
l.add(Tuple2.create(src.getColumn(eltFacture.getTable().getField("T_HA")), Type.SOMME));
}
l.add(eltFacture.getTable().getField("T_HT"));
l.add(eltFacture.getTable().getField("T_TTC"));
final IListTotalPanel total = new IListTotalPanel(this.listeFact.getListe(), l);
l.add(Tuple2.create(totalAvoirHT, Type.SOMME));
l.add(Tuple2.create(src.getColumn(eltFacture.getTable().getField("T_HT")), Type.SOMME));
l.add(Tuple2.create(src.getColumn(eltFacture.getTable().getField("T_TTC")), Type.SOMME));
final IListTotalPanel total = new IListTotalPanel(this.listeFact.getListe(), l, null, "Total");
cFacture.weighty = 0;
cFacture.fill = GridBagConstraints.NONE;
cFacture.gridy++;
173,7 → 228,6
total.setOpaque(false);
panelFacture.add(total, cFacture);
 
 
IListFilterDatePanel filterDate = new IListFilterDatePanel(this.listeFact.getListe(), eltFacture.getTable().getField("DATE"), IListFilterDatePanel.getDefaultMap());
cFacture.weighty = 0;
cFacture.fill = GridBagConstraints.HORIZONTAL;
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/ui/InvoicePercentRenderer.java
New file
0,0 → 1,132
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.invoice.ui;
 
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
 
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
 
import org.openconcerto.ui.VerticalLayout;
 
public class InvoicePercentRenderer extends JPanel {
private int v = 0;
private JLabel l1 = new JLabel("100 %", SwingConstants.CENTER);
private JLabel l2 = new JLabel("100 %", SwingConstants.CENTER);
 
private boolean affacturer = false;
private boolean soldeAvoir = false;
 
public InvoicePercentRenderer() {
l1.setForeground(Color.WHITE);
l2.setForeground(Color.BLACK);
}
 
public void setValue(Number value) {
if (value == null) {
value = Integer.valueOf(0);
}
v = value.intValue();
final String text = v + " %";
l1.setText(text);
l2.setText(text);
}
 
@Override
public void setBounds(int x, int y, int width, int height) {
l1.setBounds(x, y, width, height);
l2.setBounds(x, y, width, height);
super.setBounds(x, y, width, height);
}
 
@Override
public Dimension getPreferredSize() {
return l1.getPreferredSize();
}
 
@Override
public Dimension getMinimumSize() {
return l1.getMinimumSize();
}
 
@Override
public Dimension getMaximumSize() {
return l1.getMaximumSize();
}
 
public void setSoldeAvoir(boolean soldeAvoir) {
this.soldeAvoir = soldeAvoir;
}
 
public void setAffacturer(boolean affacturer) {
this.affacturer = affacturer;
}
 
@Override
public void paint(Graphics g) {
int width = (int) (this.getWidth() * v) / 100;
int height = this.getHeight();
int y = 0;
if (g.getClipBounds() != null) {
height = g.getClipBounds().height;
y = g.getClipBounds().y;
}
if (v < 100) {
g.setColor(Color.WHITE);
g.fillRect(0, y, this.getWidth(), height);
}
if (width > 0) {
 
if (v < 10) {
g.setColor(Color.ORANGE);
} else if (v >= 100) {
if (this.affacturer) {
g.setColor(new Color(238, 200, 126));
} else if (this.soldeAvoir) {
g.setColor(new Color(102, 153, 238));
} else {
g.setColor(new Color(25, 169, 4));
}
} else {
g.setColor(new Color(70, 130, 180));
}
g.fillRect(0, y, width, height);
g.setClip(0, y, width, height);
l1.paint(g);
}
g.setClip(width, y, this.getWidth() - width, height);
l2.paint(g);
 
}
 
public static void main(String[] args) {
JFrame f = new JFrame();
JPanel p = new JPanel();
p.setLayout(new VerticalLayout());
for (int i = 0; i <= 100; i += 4) {
InvoicePercentRenderer r1 = new InvoicePercentRenderer();
r1.setValue(i);
r1.setSize(100, 16);
p.add(r1);
 
}
f.setContentPane(p);
f.setSize(100, 500);
f.setVisible(true);
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/component/SaisieVenteFactureSQLComponent.java
49,7 → 49,6
import org.openconcerto.sql.element.ElementSQLObject;
import org.openconcerto.sql.element.SQLComponent;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.element.SQLComponent.Mode;
import org.openconcerto.sql.model.SQLBackgroundTableCache;
import org.openconcerto.sql.model.SQLBase;
import org.openconcerto.sql.model.SQLInjector;
56,7 → 55,9
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLSelectJoin;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.UndefinedRowValuesCache;
import org.openconcerto.sql.model.Where;
691,9 → 692,25
this.addView(acompteCmd, "ACOMPTE_COMMANDE");
}
 
if (this.getTable().getFieldsName().contains("POURCENT_RG") && prefs.getBoolean(GestionCommercialeGlobalPreferencePanel.POURCENT_RG, false)) {
// RG
c.gridy++;
c.gridx = 0;
c.weightx = 0;
c.weighty = 0;
c.gridwidth = 1;
c.fill = GridBagConstraints.HORIZONTAL;
this.add(new JLabel(getLabelFor("POURCENT_RG"), SwingConstants.RIGHT), c);
c.gridx++;
c.weightx = 1;
JTextField fieldRG = new JTextField();
this.add(fieldRG, c);
this.addView(fieldRG, "POURCENT_RG");
}
 
c.gridy++;
c.gridx = 0;
c.weightx = 1;
c.weighty = 1;
c.gridwidth = GridBagConstraints.REMAINDER;
c.fill = GridBagConstraints.BOTH;
1008,7 → 1025,7
 
});
 
this.selAvoir.addValueListener(new PropertyChangeListener() {
this.selAvoir.addModelListener("wantedID", new PropertyChangeListener() {
 
public void propertyChange(PropertyChangeEvent evt) {
refreshText();
1061,7 → 1078,7
 
this.changeCompteListener = new PropertyChangeListener() {
public void propertyChange(PropertyChangeEvent evt) {
SQLSelect sel = new SQLSelect(getTable().getBase());
SQLSelect sel = new SQLSelect();
sel.addSelect(SaisieVenteFactureSQLComponent.this.client.getTable().getKey());
Where where = new Where(SaisieVenteFactureSQLComponent.this.client.getTable().getField("ID_COMPTE_PCE"), "=", SaisieVenteFactureSQLComponent.this.compteSel.getValue());
sel.setWhere(where);
1225,12 → 1242,10
if (n != null) {
netAPayer = n.longValue();
ttc = n.longValue();
}
 
if (this.selAvoir.getSelectedId() > 1) {
SQLTable tableAvoir = Configuration.getInstance().getDirectory().getElement("AVOIR_CLIENT").getTable();
if (n != null) {
SQLRow rowAvoir = tableAvoir.getRow(this.selAvoir.getSelectedId());
if (this.selAvoir.getWantedID() > 1) {
final SQLTable tableAvoir = getElement().getForeignElement("ID_AVOIR_CLIENT").getTable();
final SQLRow rowAvoir = tableAvoir.getRow(this.selAvoir.getWantedID());
long totalAvoir = ((Number) rowAvoir.getObject("MONTANT_TTC")).longValue();
totalAvoir -= ((Number) rowAvoir.getObject("MONTANT_SOLDE")).longValue();
if (getSelectedID() > 1) {
1251,6 → 1266,7
netAPayer = l;
}
}
 
if (this.gestionTimbre) {
Long timbre = this.totalTimbre.getValue();
if (timbre != null) {
1306,6 → 1322,17
if (r != null) {
// FIXME Mettre un droit pour autoriser la modification d'une facture lettrée ou pointée
if (!r.isUndefined() && r.getObject("ID_MOUVEMENT") != null && !r.isForeignEmpty("ID_MOUVEMENT")) {
 
if (containsChequeDeposer(r)) {
SwingUtilities.invokeLater(new Runnable() {
 
@Override
public void run() {
JOptionPane.showMessageDialog(null, "Attention cette facture est référencée par un chèque déposé en banque. Vous ne pourrez pas valider les modifications!");
}
});
}
 
SQLTable tableEcr = getTable().getTable("ECRITURE");
SQLTable tableMvt = getTable().getTable("MOUVEMENT");
SQLTable tablePiece = getTable().getTable("PIECE");
1379,6 → 1406,30
} // nomClient.addValueListener(changeClientListener);
}
 
private boolean containsChequeDeposer(SQLRowAccessor r) {
if (!r.isUndefined() && r.getObject("ID_MOUVEMENT") != null && !r.isForeignEmpty("ID_MOUVEMENT")) {
final SQLTable tableCheque = getTable().getTable("CHEQUE_A_ENCAISSER");
SQLRowValues rowValsCheque = new SQLRowValues(tableCheque);
rowValsCheque.putNulls("ENCAISSE");
rowValsCheque.putRowValues("ID_MOUVEMENT").putRowValues("ID_PIECE");
 
final int idPiece = r.getForeign("ID_MOUVEMENT").getInt("ID_PIECE");
final SQLRowValuesListFetcher createFetcher = SQLRowValuesListFetcher.create(rowValsCheque);
createFetcher.addSelTransf(new ITransformer<SQLSelect, SQLSelect>() {
@Override
public SQLSelect transformChecked(SQLSelect input) {
final SQLSelectJoin joinFromField = input.getJoinFromField(r.getTable().getForeignTable("ID_MOUVEMENT").getField("ID_PIECE"));
input.setWhere(new Where(tableCheque.getField("ENCAISSE"), "=", Boolean.TRUE).and(new Where(joinFromField.getJoinedTable().getKey(), "=", idPiece)));
return input;
}
}, 0);
final List<SQLRowValues> fetch = createFetcher.fetch();
return !fetch.isEmpty();
}
return false;
 
}
 
private String getInitialesFromVerif(SQLRow row) {
String s = "";
 
1443,10 → 1494,22
rowVals.update();
}
} else {
rowFactureOld = this.getTable().getRow(getSelectedID());
if (containsChequeDeposer(rowFactureOld)) {
SwingUtilities.invokeLater(new Runnable() {
 
@Override
public void run() {
JOptionPane.showMessageDialog(null,
"Cette facture est référencée par un chèque déposé en banque. Impossible de valider les modifications!\n Supprimer le dépôt de chèque avant de modifier la facture.");
}
});
return idSaisieVF;
}
 
if (JOptionPane.showConfirmDialog(this, "Attention en modifiant cette facture, vous supprimerez les chéques et les échéances associés. Continuer?", "Modification de facture",
JOptionPane.YES_NO_OPTION) == JOptionPane.YES_OPTION) {
// On recupere l'ancien total HT
rowFactureOld = this.getTable().getRow(getSelectedID());
lFactureOld = ((Number) rowFactureOld.getObject("T_HT")).longValue();
 
super.update();
1558,6 → 1621,7
}
if (attempt > 0) {
SwingUtilities.invokeLater(new Runnable() {
 
public void run() {
JOptionPane.showMessageDialog(null, "Le numéro a été actualisé en " + num);
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/element/SaisieVenteFactureSQLElement.java
30,6 → 30,7
import org.openconcerto.erp.core.sales.invoice.component.SaisieVenteFactureSQLComponent;
import org.openconcerto.erp.core.sales.invoice.report.VenteFactureXmlSheet;
import org.openconcerto.erp.core.sales.invoice.ui.DateReglementRenderer;
import org.openconcerto.erp.core.sales.invoice.ui.InvoicePercentRenderer;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.erp.core.sales.shipment.component.BonDeLivraisonSQLComponent;
import org.openconcerto.erp.core.supplychain.stock.element.MouvementStockSQLElement;
66,26 → 67,26
import org.openconcerto.sql.view.EditPanel;
import org.openconcerto.sql.view.EditPanel.EditMode;
import org.openconcerto.sql.view.EditPanelListener;
import org.openconcerto.sql.view.IListeFilter;
import org.openconcerto.sql.view.list.BaseSQLTableModelColumn;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.IListeAction.IListeEvent;
import org.openconcerto.sql.view.list.ITableModel;
import org.openconcerto.sql.view.list.RowAction;
import org.openconcerto.sql.view.list.RowAction.PredicateRowAction;
import org.openconcerto.sql.view.list.SQLTableModelSource;
import org.openconcerto.sql.view.list.action.ListEvent;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.FrameUtil;
import org.openconcerto.ui.table.PercentTableCellRenderer;
import org.openconcerto.utils.CollectionUtils;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.ListMap;
import org.openconcerto.utils.TableSorter;
import org.openconcerto.utils.Tuple2;
import org.openconcerto.utils.cc.IClosure;
import org.openconcerto.utils.cc.ITransformer;
import org.openconcerto.utils.i18n.TranslationManager;
 
import java.awt.Component;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
110,7 → 111,9
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTable;
import javax.swing.SwingUtilities;
import javax.swing.table.DefaultTableCellRenderer;
 
import org.apache.commons.dbutils.handlers.ArrayListHandler;
 
140,6 → 143,7
super(TABLENAME, "une facture", "factures");
 
GlobalMapper.getInstance().map(VenteFactureSituationSQLComponent.ID, new PartialInvoiceEditGroup());
GlobalMapper.getInstance().map(VenteFactureSituationSQLComponent.ID_PREVISIONNELLE, new PartialInvoiceEditGroup());
addComponentFactory(VenteFactureSituationSQLComponent.ID, new ITransformer<Tuple2<SQLElement, String>, SQLComponent>() {
 
@Override
148,7 → 152,16
return new VenteFactureSituationSQLComponent(SaisieVenteFactureSQLElement.this);
}
});
addComponentFactory(VenteFactureSituationSQLComponent.ID_PREVISIONNELLE, new ITransformer<Tuple2<SQLElement, String>, SQLComponent>() {
 
@Override
public SQLComponent transformChecked(Tuple2<SQLElement, String> input) {
 
return new VenteFactureSituationSQLComponent(SaisieVenteFactureSQLElement.this);
}
});
GlobalMapper.getInstance().map(VenteFactureSoldeSQLComponent.ID, new VenteFactureSoldeEditGroup());
GlobalMapper.getInstance().map(VenteFactureSoldeSQLComponent.ID_PREVISIONNELLE, new VenteFactureSoldeEditGroup());
addComponentFactory(VenteFactureSoldeSQLComponent.ID, new ITransformer<Tuple2<SQLElement, String>, SQLComponent>() {
 
@Override
157,7 → 170,15
return new VenteFactureSoldeSQLComponent(SaisieVenteFactureSQLElement.this);
}
});
addComponentFactory(VenteFactureSoldeSQLComponent.ID_PREVISIONNELLE, new ITransformer<Tuple2<SQLElement, String>, SQLComponent>() {
 
@Override
public SQLComponent transformChecked(Tuple2<SQLElement, String> input) {
 
return new VenteFactureSoldeSQLComponent(SaisieVenteFactureSQLElement.this);
}
});
 
final boolean affact = UserRightsManager.getCurrentUserRights().haveRight(NXRights.ACCES_RETOUR_AFFACTURAGE.getCode());
List<RowAction> l = new ArrayList<RowAction>(5);
PredicateRowAction actionBL = new PredicateRowAction(new AbstractAction() {
351,7 → 372,7
@Override
protected synchronized void _initTableSource(final SQLTableModelSource table) {
super._initTableSource(table);
 
addCommercialFilter(table, getTable().getField("ID_COMMERCIAL"));
final BaseSQLTableModelColumn colAvancement = new BaseSQLTableModelColumn("Avancement réglement", BigDecimal.class) {
 
@Override
362,6 → 383,8
 
@Override
public Set<FieldPath> getPaths() {
Path pFact = new Path(SaisieVenteFactureSQLElement.this.getTable());
 
Path p = new Path(SaisieVenteFactureSQLElement.this.getTable());
p = p.add(getTable().getTable("ECHEANCE_CLIENT"));
 
368,14 → 391,29
Path p2 = new Path(SaisieVenteFactureSQLElement.this.getTable());
p2 = p2.add(getTable().getField("ID_AVOIR_CLIENT"));
 
return CollectionUtils.createSet(new FieldPath(p, "MONTANT"), new FieldPath(p, "REG_COMPTA"), new FieldPath(p, "REGLE"), new FieldPath(p2, "MONTANT_TTC"));
return CollectionUtils.createSet(new FieldPath(pFact, "NET_A_PAYER"), new FieldPath(pFact, "AFFACTURAGE"), new FieldPath(p, "MONTANT"), new FieldPath(p, "REG_COMPTA"),
new FieldPath(p, "REGLE"), new FieldPath(p2, "MONTANT_TTC"));
}
};
table.getColumns().add(colAvancement);
colAvancement.setRenderer(new PercentTableCellRenderer());
colAvancement.setRenderer(new DefaultTableCellRenderer() {
private InvoicePercentRenderer r = new InvoicePercentRenderer();
 
@Override
public Component getTableCellRendererComponent(JTable jtable, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
 
TableSorter sorter = (TableSorter) jtable.getModel();
SQLRowValues row2 = ((ITableModel) sorter.getTableModel()).getRow(row).getRow();
r.setSoldeAvoir(row2.getLong("NET_A_PAYER") == 0);
r.setAffacturer(row2.getTable().contains("AFFACTURAGE") && row2.getBoolean("AFFACTURAGE"));
r.setValue((Number) value);
 
return r;
}
});
 
}
 
protected List<String> getComboFields() {
final List<String> l = new ArrayList<String>();
l.add("NUMERO");
386,6 → 424,7
public Set<String> getReadOnlyFields() {
Set<String> s = new HashSet<String>(1);
s.add("CONTROLE_TECHNIQUE");
s.add("PREVISIONNELLE");
return s;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/element/EcheanceClientSQLElement.java
28,6 → 28,7
import org.openconcerto.erp.core.sales.invoice.report.SituationCompteClientPanel;
import org.openconcerto.erp.core.sales.invoice.report.VenteFactureXmlSheet;
import org.openconcerto.erp.core.sales.invoice.ui.DecaleEcheancePanel;
import org.openconcerto.erp.preferences.GestionCommercialeGlobalPreferencePanel;
import org.openconcerto.erp.rights.ComptaUserRight;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.BaseSQLComponent;
48,6 → 49,7
import org.openconcerto.sql.model.graph.Link;
import org.openconcerto.sql.model.graph.Path;
import org.openconcerto.sql.model.graph.PathBuilder;
import org.openconcerto.sql.preferences.SQLPreferences;
import org.openconcerto.sql.request.ListSQLRequest;
import org.openconcerto.sql.sqlobject.ElementComboBox;
import org.openconcerto.sql.users.rights.UserRightsManager;
132,6 → 134,24
}
 
{
 
PredicateRowAction action = new PredicateRowAction(new AbstractAction("Ajouter un commentaire") {
 
@Override
public void actionPerformed(ActionEvent arg0) {
 
SQLRow row = IListe.get(arg0).fetchSelectedRow();
 
final UpdateCommEchFrame frame = UpdateCommEchFrame.getFrame();
frame.select(row);
frame.setVisible(true);
}
}, false);
action.setPredicate(IListeEvent.getSingleSelectionPredicate());
getRowActions().add(action);
}
 
{
PredicateRowAction action = new PredicateRowAction(new AbstractAction("Envoyer un mail de relance") {
 
@Override
142,7 → 162,7
"Souhaitez vous envoyer un email de relance pour toutes les factures\ndont l'échéance est dépassée?\nLes relances ne seront pas envoyées si les factures ont déjà  une relance de moins d'un mois. ",
"Relance automatique", JOptionPane.YES_NO_OPTION);
if (result == JOptionPane.YES_OPTION) {
EmailTemplate.askTemplate(iListe, getTable().getDBRoot(), new ValueListener() {
EmailTemplate.askTemplate(iListe, getTable().getDBRoot(), getTable().getName(), new ValueListener() {
 
@Override
public void valueSelected(Object value) {
164,10 → 184,10
if (rowValues.isEmpty()) {
JOptionPane.showMessageDialog(iListe, "Aucune relance à  envoyer.");
} else {
for (SQLRowValues row : rowValues) {
sendMail(row.asRow(), template);
 
sendMail(rowValues, template);
 
}
}
} catch (Exception e) {
ExceptionHandler.handle("erreur lors de l'envoi", e);
}
186,7 → 206,7
} else {
final SQLTable primaryTable = iListe.getRequest().getPrimaryTable();
final List<Integer> selectedIDs = iListe.getSelection().getSelectedIDs();
EmailTemplate.askTemplate(iListe, getTable().getDBRoot(), new ValueListener() {
EmailTemplate.askTemplate(iListe, getTable().getDBRoot(), getTable().getName(), new ValueListener() {
 
@Override
public void valueSelected(Object value) {
196,9 → 216,9
try {
EmailTemplate template = (EmailTemplate) value;
final List<SQLRow> rows = SQLRowListRSH.fetch(primaryTable, selectedIDs);
for (SQLRow row : rows) {
sendMail(row, template);
}
 
sendMail(rows, template);
 
} catch (Exception e) {
ExceptionHandler.handle("erreur lors de l'envoi", e);
}
362,39 → 382,44
}
 
 
private void sendMail(final SQLRow row, EmailTemplate template) throws Exception {
private void sendMail(final List<? extends SQLRowAccessor> rows, EmailTemplate template) throws Exception {
ListMap<Integer, SQLRow> mapByCustomer = new ListMap<>();
for (SQLRowAccessor sqlRow : rows) {
mapByCustomer.add(sqlRow.getForeignID("ID_CLIENT"), sqlRow.asRow());
}
for (List<SQLRow> sqlRows : mapByCustomer.values()) {
sendCustomerMail(sqlRows, template);
}
}
 
SQLBase base = ((ComptaPropsConfiguration) Configuration.getInstance()).getSQLBaseSociete();
private void sendCustomerMail(final List<SQLRow> rows, EmailTemplate template) throws Exception {
 
int idMvtSource = MouvementSQLElement.getSourceId(row.getInt("ID_MOUVEMENT"));
SQLRow rowMvtSource = base.getTable("MOUVEMENT").getRow(idMvtSource);
int idMvtSource = MouvementSQLElement.getSourceId(rows.get(0).getInt("ID_MOUVEMENT"));
SQLRow rowMvtSource = getTable().getTable("MOUVEMENT").getRow(idMvtSource);
 
if (!rowMvtSource.getString("SOURCE").equalsIgnoreCase("SAISIE_VENTE_FACTURE")) {
return;
}
int idFact = rowMvtSource.getInt("IDSOURCE");
SQLRow rowFacture = base.getTable("SAISIE_VENTE_FACTURE").getRow(idFact);
 
final VenteFactureXmlSheet sheet = new VenteFactureXmlSheet(rowFacture);
 
Set<SQLField> setContact = null;
SQLTable tableContact = Configuration.getInstance().getRoot().findTable("CONTACT");
setContact = row.getTable().getForeignKeys(tableContact);
setContact = rows.get(0).getTable().getForeignKeys(tableContact);
 
Set<SQLField> setClient = null;
SQLTable tableClient = ((ComptaPropsConfiguration) Configuration.getInstance()).getSQLBaseSociete().getTable("CLIENT");
setClient = row.getTable().getForeignKeys(tableClient);
setClient = rows.get(0).getTable().getForeignKeys(tableClient);
 
// Récupération du mail du client
String mail = "";
for (SQLField field : setContact) {
if (mail == null || mail.trim().length() == 0) {
mail = row.getForeignRow(field.getName()).getString("EMAIL");
mail = rows.get(0).getForeignRow(field.getName()).getString("EMAIL");
}
}
 
for (SQLField field : setClient) {
SQLRow rowCli = row.getForeignRow(field.getName());
SQLRow rowCli = rows.get(0).getForeignRow(field.getName());
if (mail == null || mail.trim().length() == 0) {
mail = rowCli.getString("MAIL");
}
401,26 → 426,41
}
final String adresseMail = mail;
 
MailRelanceCreator creator = new MailRelanceCreator(template, row);
File[] files = new File[rows.size()];
 
MailRelanceCreator creator = new MailRelanceCreator(template, rows);
final String references = creator.getObject();
final String text = creator.getValue();
 
int i = 0;
for (SQLRow row : rows) {
final File f;
 
SQLRow rowFacture = getTable().getTable("SAISIE_VENTE_FACTURE").getRow(row.getForeignID("ID_SAISIE_VENTE_FACTURE"));
 
final VenteFactureXmlSheet sheet = new VenteFactureXmlSheet(rowFacture);
 
f = sheet.getOrCreatePDFDocumentFile(true);
files[i] = f.getAbsoluteFile();
i++;
}
 
EmailComposer.getInstance().compose(adresseMail, references, text, f.getAbsoluteFile());
EmailComposer.getInstance().compose(adresseMail, references, text, files);
 
long montant = 0;
for (SQLRow rowEch : rows) {
montant += rowEch.getLong("MONTANT");
}
// Création d'une relance
String numero = NumerotationAutoSQLElement.getNextNumero(RelanceSQLElement.class);
SQLRowValues rowValsR = new SQLRowValues(row.getTable().getTable("RELANCE"));
SQLRowValues rowValsR = new SQLRowValues(getTable().getTable("RELANCE"));
rowValsR.put("DATE", new Date());
rowValsR.put("NUMERO", numero);
rowValsR.put("ID_CLIENT", row.getForeignID("ID_CLIENT"));
rowValsR.put("ID_SAISIE_VENTE_FACTURE", row.getForeignID("ID_SAISIE_VENTE_FACTURE"));
rowValsR.put("MONTANT", row.getObject("MONTANT"));
rowValsR.put("ID_CLIENT", rows.get(0).getForeignID("ID_CLIENT"));
rowValsR.put("ID_SAISIE_VENTE_FACTURE", rows.get(0).getForeignID("ID_SAISIE_VENTE_FACTURE"));
rowValsR.put("MONTANT", montant);
rowValsR.put("INFOS", "Email");
rowValsR.put("ID_ECHEANCE_CLIENT", row.getID());
rowValsR.put("ID_ECHEANCE_CLIENT", rows.get(0).getID());
 
rowValsR.insert();
 
433,14 → 473,17
rowVals.update(2);
 
// Incrémentation du nombre de relance
int nbRelance = row.getInt("NOMBRE_RELANCE");
for (SQLRow rowEch : rows) {
 
int nbRelance = rowEch.getInt("NOMBRE_RELANCE");
nbRelance++;
 
SQLRowValues rowValsEch = new SQLRowValues(row.getTable());
SQLRowValues rowValsEch = new SQLRowValues(rowEch.getTable());
rowValsEch.put("NOMBRE_RELANCE", nbRelance);
rowValsEch.put("DATE_LAST_RELANCE", new Date());
 
rowValsEch.update(row.getID());
rowValsEch.update(rowEch.getID());
}
 
}
 
461,6 → 504,9
l.add("ID_MOUVEMENT");
l.add("NOMBRE_RELANCE");
l.add("INFOS");
if (SQLPreferences.getMemCached(getTable().getDBRoot()).getBoolean(GestionCommercialeGlobalPreferencePanel.POURCENT_RG, false)) {
l.add("RG");
}
l.add("DATE_LAST_RELANCE");
return l;
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/element/UpdateCommEchFrame.java
New file
0,0 → 1,144
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.invoice.element;
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.component.ITextArea;
import org.openconcerto.utils.ExceptionHandler;
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.sql.SQLException;
 
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
 
public class UpdateCommEchFrame extends JFrame {
 
private JTextField numero = new JTextField();
private JTextField client = new JTextField(30);
private ITextArea comm = new ITextArea(5, 50);
SQLRow row;
 
public static UpdateCommEchFrame getFrame() {
 
UpdateCommEchFrame frame = new UpdateCommEchFrame();
 
frame.pack();
frame.setLocationRelativeTo(null);
return frame;
}
 
private JPanel createPanel() {
JPanel panel = new JPanel(new GridBagLayout());
 
GridBagConstraints c = new DefaultGridBagConstraints();
panel.add(new JLabel("Facture"), c);
c.gridx++;
c.weightx = 1;
panel.add(this.numero, c);
this.numero.setEditable(false);
c.gridy++;
c.gridx = 0;
c.weightx = 0;
panel.add(new JLabel("Client"), c);
 
c.gridx++;
c.weightx = 1;
panel.add(this.client, c);
this.client.setEditable(false);
c.gridy++;
c.gridx = 0;
c.weightx = 0;
panel.add(new JLabel("Commentaires"), c);
 
c.gridx++;
c.fill = GridBagConstraints.BOTH;
c.weighty = 1;
c.weightx = 1;
panel.add(this.comm, c);
 
c.gridy++;
c.gridx = 0;
c.weighty = 0;
c.weightx = 0;
c.gridwidth = GridBagConstraints.REMAINDER;
c.anchor = GridBagConstraints.CENTER;
c.fill = GridBagConstraints.NONE;
JButton apply = new JButton("Valider");
apply.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
try {
update();
} catch (SQLException e1) {
ExceptionHandler.handle("Une erreur est survenue lors de la mise à jour des commentaires!", e1);
} finally {
dispose();
}
}
});
panel.add(apply, c);
return panel;
}
 
public UpdateCommEchFrame() {
super("Modification des commentaires");
 
this.getContentPane().add(createPanel());
 
}
 
public void select(SQLRow row) {
this.row = row;
if (row == null) {
 
this.comm.setText("");
this.numero.setText("");
this.client.setText("");
return;
} else {
 
this.comm.setText(row.getString("INFOS"));
this.numero.setText(row.getForeign("ID_MOUVEMENT").getForeign("ID_PIECE").getString("NOM"));
 
this.client.setText(row.getForeign("ID_CLIENT").getString("NOM"));
}
 
}
 
private void update() throws SQLException {
if (this.row != null) {
 
SQLRowValues rowValues = this.row.createEmptyUpdateRow();
 
rowValues.put("INFOS", this.comm.getText());
 
rowValues.update();
 
}
 
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/report/EtatStockInventaireXmlSheet.java
16,6 → 16,7
import org.openconcerto.erp.generationDoc.AbstractListeSheetXml;
import org.openconcerto.erp.preferences.PrinterNXProps;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.element.SQLElementDirectory;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowListRSH;
35,6 → 36,7
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;
 
public class EtatStockInventaireXmlSheet extends AbstractListeSheetXml {
47,13 → 49,14
private Date date;
private SQLElement eltArticle;
private SQLElement eltStock;
private Set<Number> etatStockIds;
 
public EtatStockInventaireXmlSheet(SQLRow etatStock) {
public EtatStockInventaireXmlSheet(SQLElementDirectory dir, Set<Number> etatStockIds) {
super();
this.row = etatStock;
 
this.etatStockIds = etatStockIds;
this.eltArticle = dir.getElement("ARTICLE");
this.eltStock = dir.getElement("STOCK");
this.printer = PrinterNXProps.getInstance().getStringProperty("BonPrinter");
 
}
 
@Override
76,8 → 79,9
 
protected void createListeValues() {
 
SQLRowValues rowVals = new SQLRowValues(this.row.getTable().getTable("ETAT_STOCK_ELEMENT"));
SQLRowValues rowVals = new SQLRowValues(this.eltArticle.getTable().getTable("ETAT_STOCK_ELEMENT"));
rowVals.put("QTE", null);
rowVals.putRowValues("ID_ETAT_STOCK").putRowValues("ID_DEPOT_STOCK").putNulls("NOM");
SQLRowValues rowValsArt = rowVals.putRowValues("ID_ARTICLE");
rowValsArt.put("ID_FAMILLE_ARTICLE", null);
rowValsArt.put("CODE", null);
88,9 → 92,9
rowValsArt.putRowValues("ID_ARTICLE_DECLINAISON_COULEUR").putNulls("NOM");
 
SQLRowValuesListFetcher fetch = SQLRowValuesListFetcher.create(rowVals);
List<SQLRowValues> values = fetch.fetch(new Where(rowVals.getTable().getField("ID_ETAT_STOCK"), "=", this.row.getID()));
List<SQLRowValues> values = fetch.fetch(Where.inValues(rowVals.getTable().getField("ID_ETAT_STOCK"), this.etatStockIds));
 
final SQLTable tableF = this.row.getTable().getTable("FAMILLE_ARTICLE");
final SQLTable tableF = this.eltArticle.getTable().getTable("FAMILLE_ARTICLE");
SQLSelect selFam = new SQLSelect();
selFam.addSelect(tableF.getKey());
selFam.addSelect(tableF.getField("NOM"));
102,7 → 106,7
mapF.put(sqlRow.getID(), sqlRow);
}
 
final SQLTable tableFourn = this.row.getTable().getTable("FOURNISSEUR");
final SQLTable tableFourn = this.eltArticle.getTable().getTable("FOURNISSEUR");
SQLSelect selFourn = new SQLSelect();
selFourn.addSelect(tableFourn.getKey());
selFourn.addSelect(tableFourn.getField("NOM"));
117,9 → 121,25
Map<Line, Map<Line, List<Line>>> myValues = new TreeMap<Line, Map<Line, List<Line>>>(new Comparator<Line>() {
@Override
public int compare(Line o1, Line o2) {
// TODO ajouter tri sur taille et couleur
return o1.getNomArt().compareTo(o2.getNomArt());
 
final int compareDepot = o1.getDepot().compareTo(o2.getDepot());
if (compareDepot == 0) {
int compareNom = o1.getNomArt().compareTo(o2.getNomArt());
 
if (compareNom == 0) {
int compareCouleur = o1.getCouleur().compareTo(o2.getCouleur());
if (compareCouleur == 0) {
return o1.getTaille().compareTo(o2.getTaille());
} else {
return compareCouleur;
}
} else {
return compareNom;
}
} else {
return compareDepot;
}
}
});
Line lineTotal = new Line("Total", "", BigDecimal.ZERO, BigDecimal.ZERO);
final HashMap<Integer, String> style = new HashMap<Integer, String>();
140,7 → 160,12
if (rowValsArticle.getObject("ID_ARTICLE_DECLINAISON_TAILLE") != null && !rowValsArticle.isForeignEmpty("ID_ARTICLE_DECLINAISON_TAILLE")) {
taille = rowValsArticle.getForeign("ID_ARTICLE_DECLINAISON_TAILLE").getString("NOM");
}
Line lineArt = new Line(rowF == null || rowF.isUndefined() ? "Sans famille" : rowF.getString("NOM"), taille, couleur, nomArticle, rowValsArticle.getString("CODE"), ha, qte);
String depot = "Principal";
final SQLRowAccessor nonEmptyForeignDepot = vals.getForeign("ID_ETAT_STOCK").getNonEmptyForeign("ID_DEPOT_STOCK");
if (nonEmptyForeignDepot != null) {
depot = nonEmptyForeignDepot.getString("NOM");
}
Line lineArt = new Line(rowF == null || rowF.isUndefined() ? "Sans famille" : rowF.getString("NOM"), taille, couleur, nomArticle, rowValsArticle.getString("CODE"), depot, ha, qte);
 
// Init des lines familles
 
240,14 → 265,15
private final String famille;
private final String taille;
private final String couleur;
private final String depot;
private BigDecimal totalHA;
private BigDecimal qte;
 
public Line(String nomArt, String codeArt, BigDecimal totalHA, BigDecimal qte) {
this("", "", "", nomArt, codeArt, totalHA, qte);
this("", "", "", nomArt, codeArt, "", totalHA, qte);
}
 
public Line(String famille, String taille, String couleur, String nomArt, String codeArt, BigDecimal totalHA, BigDecimal qte) {
public Line(String famille, String taille, String couleur, String nomArt, String codeArt, String depot, BigDecimal totalHA, BigDecimal qte) {
this.famille = famille;
this.nomArt = nomArt;
this.taille = taille;
255,6 → 281,7
this.codeArt = codeArt;
this.totalHA = totalHA;
this.qte = qte;
this.depot = depot;
}
 
public BigDecimal getQte() {
273,6 → 300,18
return totalHA;
}
 
public String getDepot() {
return depot;
}
 
public String getCouleur() {
return couleur;
}
 
public String getTaille() {
return taille;
}
 
public void add(Line l) {
this.totalHA = this.totalHA.add(l.getTotalHA());
this.qte = this.qte.add(l.getQte());
285,6 → 324,7
m.put("NOM", getNomArt());
m.put("TAILLE", this.taille);
m.put("COULEUR", this.couleur);
m.put("DEPOT", this.depot);
m.put("QTE", getQte());
m.put("TOTAL_HA", getTotalHA());
return m;
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/report/SituationCompteXmlSheet.java
77,7 → 77,7
final SQLTable echTable = eltEch.getTable();
SQLRowValues rowVals = new SQLRowValues(echTable);
rowVals.putNulls("DATE", "MONTANT");
rowVals.putRowValues("ID_SAISIE_VENTE_FACTURE").putNulls("NUMERO", "NET_A_PAYER", "DATE", "NOM");
rowVals.putRowValues("ID_SAISIE_VENTE_FACTURE").putNulls("NUMERO", "NET_A_PAYER", "T_AVOIR_TTC", "DATE", "NOM").putRowValues("ID_AVOIR_CLIENT").putNulls("NUMERO", "DATE");
Where w = new Where(echTable.getField("REGLE"), "=", Boolean.FALSE);
w = w.and(new Where(echTable.getField("REG_COMPTA"), "=", Boolean.FALSE));
w = w.and(new Where(echTable.getField("ID_CLIENT"), "=", row.getID()));
92,7 → 92,14
return o1.getDate("DATE").compareTo(o2.getDate("DATE"));
}
});
Collections.sort(result, new Comparator<SQLRowValues>() {
@Override
public int compare(SQLRowValues o1, SQLRowValues o2) {
 
return o1.getDate("DATE").compareTo(o2.getDate("DATE"));
}
});
 
List<Map<String, Object>> listValues = new ArrayList<Map<String, Object>>();
Map<Integer, String> styleValues = new HashMap<Integer, String>();
BigDecimal totalRegle = BigDecimal.ZERO;
117,9 → 124,12
final BigDecimal montantFact = new BigDecimal(rowFact.getLong("NET_A_PAYER"));
regle = montantFact.subtract(montantDu);
mValues.put("DU", montantFact.movePointLeft(2));
if (!rowFact.isForeignEmpty("ID_AVOIR_CLIENT")) {
mValues.put("AVOIR_TTC", new BigDecimal(rowFact.getLong("T_AVOIR_TTC")).movePointLeft(2));
mValues.put("AVOIR_NUMERO", rowFact.getForeign("ID_AVOIR_CLIENT").getString("NUMERO"));
}
mValues.put("REGLE", montantFact.subtract(montantDu).movePointLeft(2));
mValues.put("SOLDE", montantDu.movePointLeft(2));
 
} else {
regle = BigDecimal.ZERO;
mValues.put("SOLDE", montantDu.movePointLeft(2));
167,7 → 177,6
 
}
 
 
// Avoir
final SQLTable avoirTable = echTable.getTable("AVOIR_CLIENT");
SQLRowValues rowValsAvoir = new SQLRowValues(avoirTable);
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/report/ReportingClientPanel.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
23,6 → 23,7
import org.openconcerto.ui.JDate;
import org.openconcerto.ui.JLabelBold;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.FileUtils;
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
29,9 → 30,11
import java.awt.event.ActionEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.io.File;
 
import javax.swing.AbstractAction;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JLabel;
import javax.swing.JPanel;
 
62,6 → 65,11
 
c.gridy++;
c.gridx = 0;
final JCheckBox boxMail = new JCheckBox("Envoie par mail");
this.add(boxMail);
boxMail.setSelected(true);
c.gridy++;
c.gridx = 0;
c.gridwidth = 1;
this.add(new JLabel("Facture émises entre le"), c);
final JDate d1 = new JDate();
87,6 → 95,7
sheet.createDocument();
// sheet.showPrintAndExport(false, false, false);
 
if (boxMail.isSelected()) {
String mail = selectedClient.getString("MAIL");
 
try {
94,6 → 103,10
} catch (Exception exn) {
ExceptionHandler.handle(null, "Impossible de créer le courriel", exn);
}
} else {
File f = sheet.getOrCreateDocumentFile();
FileUtils.openFile(f);
}
 
} catch (Exception e) {
ExceptionHandler.handle("Une erreur est survenue lors de la création du document", e);
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/report/ReportingClientXml.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
13,6 → 13,7
package org.openconcerto.erp.core.sales.invoice.report;
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.generationDoc.AbstractListeSheetXml;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.model.SQLRow;
22,6 → 23,8
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.users.User;
import org.openconcerto.sql.users.UserManager;
import org.openconcerto.utils.cc.ITransformer;
 
import java.text.DateFormat;
59,7 → 62,7
final SQLTable tableFacture = Configuration.getInstance().getDirectory().getElement("SAISIE_VENTE_FACTURE").getTable();
SQLRowValues rowValsF = new SQLRowValues(tableFacture);
rowValsF.put("ID_CLIENT", rowVals);
rowValsF.putNulls("NUMERO", "NOM", "T_HT", "T_TTC", "DATE", "INFOS");
rowValsF.putNulls("NUMERO", "NOM", "T_HT", "T_TTC", "DATE", "NET_A_PAYER", "INFOS", "T_AVOIR_TTC").putRowValues("ID_AVOIR_CLIENT").putNulls("DATE", "NUMERO");
 
final SQLTable tableEch = Configuration.getInstance().getDirectory().getElement("ECHEANCE_CLIENT").getTable();
SQLRowValues rowValsE = new SQLRowValues(tableEch);
95,6 → 98,27
mapValues.put("CLIENT", this.row.getString("NOM"));
mapValues.put("DATE", toDay.getTime());
 
final SQLRow rowSociete = ComptaPropsConfiguration.getInstanceCompta().getRowSociete();
mapValues.put("SOCIETE_NOM", rowSociete.getString("NOM"));
mapValues.put("SOCIETE_TYPE", rowSociete.getString("TYPE"));
mapValues.put("SOCIETE_SIRET", rowSociete.getString("NUM_SIRET"));
mapValues.put("SOCIETE_TVA", rowSociete.getString("NUM_NII"));
mapValues.put("SOCIETE_APE", rowSociete.getString("NUM_APE"));
mapValues.put("SOCIETE_FAX", rowSociete.getString("NUM_FAX"));
mapValues.put("SOCIETE_TEL", rowSociete.getString("NUM_TEL"));
mapValues.put("SOCIETE_ADRESSE", rowSociete.getForeign("ID_ADRESSE_COMMON").getString("RUE"));
mapValues.put("SOCIETE_ADRESSE_FULL", rowSociete.getForeign("ID_ADRESSE_COMMON").getString("RUE") + " " + rowSociete.getForeign("ID_ADRESSE_COMMON").getString("CODE_POSTAL") + " "
+ rowSociete.getForeign("ID_ADRESSE_COMMON").getString("VILLE"));
mapValues.put("SOCIETE_CODE_POSTAL", rowSociete.getForeign("ID_ADRESSE_COMMON").getString("CODE_POSTAL"));
mapValues.put("SOCIETE_VILLE", rowSociete.getForeign("ID_ADRESSE_COMMON").getString("VILLE"));
 
final User currentUser = UserManager.getInstance().getCurrentUser();
final SQLRow user = rowSociete.getTable().getTable("USER_COMMON").getRow(currentUser.getId());
mapValues.put("USER_NAME", user.getString("NOM"));
mapValues.put("USER_FIRSTNAME", user.getString("PRENOM"));
mapValues.put("USER_TEL", user.getString("TEL"));
mapValues.put("USER_MAIL", user.getString("MAIL"));
 
String upTo = "Invoices up to ";
String since = "Invoices since ";
String between = "Invoices between ";
146,6 → 170,10
 
final double ttc = sqlRowValues.getLong("T_TTC") / 100.0D;
line.put("T_TTC", ttc);
final double aPayer = sqlRowValues.getLong("NET_A_PAYER") / 100.0D;
line.put("NET_A_PAYER", aPayer);
final double avoir = sqlRowValues.getLong("T_AVOIR_TTC") / 100.0D;
line.put("T_AVOIR_TTC", avoir);
 
double du = 0;
 
169,9 → 197,9
line.put("ECHEANCE", dateEch.getTime());
 
line.put("DU", du);
line.put("REGLE", ttc - du);
line.put("REGLE", aPayer - du);
 
totalTTC += ttc;
totalTTC += aPayer;
totalDu += du;
 
if (du == 0) {
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/invoice/report/MailRelanceCreator.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
19,6 → 19,7
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.users.UserManager;
import org.openconcerto.utils.CollectionUtils;
import org.openconcerto.utils.GestionDevise;
 
import java.text.DateFormat;
25,21 → 26,33
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
 
public class MailRelanceCreator {
 
private final EmailTemplate template;
private final SQLRow rowEcheance;
private final List<SQLRow> rowEcheances;
private final Map<String, String> map;
 
public MailRelanceCreator(EmailTemplate template, SQLRow row) {
public MailRelanceCreator(EmailTemplate template, List<SQLRow> row) {
if (template == null) {
template = new EmailTemplate("defautl", getDefaultObject(), getDefaultValue(), true, "dd/MM/yyyy");
template = new EmailTemplate("default", getDefaultObject(), getDefaultValue(row.size() > 1), true, "dd/MM/yyyy");
}
this.template = template;
this.rowEcheance = row;
this.rowEcheances = row;
 
Integer client = null;
for (SQLRow sqlRow : row) {
if (client == null) {
client = sqlRow.getForeignID("ID_CLIENT");
} else if (client != sqlRow.getForeignID("ID_CLIENT")) {
throw new IllegalArgumentException("Plusieurs clients pour la relance par mail.");
}
}
 
this.map = getMapValues();
}
 
47,13 → 60,20
return "Relance {FactureNumero}";
}
 
public String getDefaultValue() {
String value = "Bonjour,\n\nSauf erreur de notre part, votre compte laisse apparaître dans nos livres un montant de {FactureRestant}€ non réglé à ce jour."
public String getDefaultValue(boolean multiple) {
final String value;
if (!multiple) {
value = "Bonjour,\n\nSauf erreur de notre part, votre compte laisse apparaître dans nos livres un montant de {FactureRestant}€ non réglé à ce jour."
+ "\nCe montant correspond à la facture {FactureNumero} datée du {FactureDate} qui a pour échéance le {FactureDateEcheance}."
+ "\nNous présumons qu'il s'agit d'un simple oubli de votre part.\n\n"
+ "Toutefois, si le paiement avait été effectué, nous vous serions très obligés de nous en communiquer la date et le mode de règlement.\n\n"
+ "Dans l'attente d’un prompt règlement,\n\n" + "Nous vous prions d\'agréer, Madame, Monsieur, l\'expression de nos sentiments distingués.";
 
} else {
value = "Bonjour,\n\nSauf erreur de notre part, votre compte laisse apparaître dans nos livres un montant de {FactureRestant}€ non réglé à ce jour."
+ "\nCe montant correspond aux factures :\n" + "{FacturesDetails}" + "\nNous présumons qu'il s'agit d'un simple oubli de votre part.\n\n"
+ "Toutefois, si le paiement avait été effectué, nous vous serions très obligés de nous en communiquer la date et le mode de règlement.\n\n"
+ "Dans l'attente d’un prompt règlement,\n\n" + "Nous vous prions d\'agréer, Madame, Monsieur, l\'expression de nos sentiments distingués.";
}
return value;
}
 
96,7 → 116,7
map.put("SocieteVille", ville);
 
SQLRow rowClient;
final SQLRow clientRowNX = this.rowEcheance.getForeignRow("ID_CLIENT");
final SQLRow clientRowNX = this.rowEcheances.get(0).getForeignRow("ID_CLIENT");
rowClient = clientRowNX;
SQLRow rowAdresse = rowClient.getForeignRow("ID_ADRESSE");
if (!clientRowNX.isForeignEmpty("ID_ADRESSE_F")) {
130,24 → 150,41
DateFormat dateFormat = new SimpleDateFormat(datePattern);
map.put("RelanceDate", dateFormat.format(d));
 
SQLRow rowFacture = this.rowEcheance.getForeignRow("ID_SAISIE_VENTE_FACTURE");
 
// Infos facture
Long lTotal = 0L;
Long lRestant = 0L;
Long lVerse = 0L;
 
// Infos facture
Long lTotal = (Long) rowFacture.getObject("T_TTC");
Long lRestant = (Long) this.rowEcheance.getObject("MONTANT");
Long lVerse = Long.valueOf(lTotal.longValue() - lRestant.longValue());
map.put("FactureNumero", rowFacture.getString("NUMERO"));
map.put("FactureReference", rowFacture.getString("NOM"));
Set<String> facturesNumero = new HashSet<>();
Set<String> facturesRef = new HashSet<>();
Set<String> facturesDate = new HashSet<>();
Set<String> facturesDetails = new HashSet<>();
for (SQLRow sqlRow : rowEcheances) {
final SQLRow foreign = sqlRow.getForeign("ID_SAISIE_VENTE_FACTURE");
lTotal += (Long) foreign.getObject("T_TTC");
lRestant += (Long) sqlRow.getObject("MONTANT");
lVerse += Long.valueOf(lTotal.longValue() - lRestant.longValue());
facturesDetails.add(foreign.getString("NUMERO") + " du " + dateFormat.format(foreign.getDate("DATE").getTime()) + " d'un montant TTC : "
+ GestionDevise.currencyToString((Long) foreign.getObject("T_TTC"), true) + "€, restant à régler " + GestionDevise.currencyToString((Long) sqlRow.getObject("MONTANT"), true)
+ "€ échéance le " + dateFormat.format(sqlRow.getDate("DATE").getTime()));
 
Date dFacture = (Date) foreign.getObject("DATE");
SQLRow modeRegRow = foreign.getForeignRow("ID_MODE_REGLEMENT");
Date dateEch = ModeDeReglementSQLElement.calculDate(modeRegRow.getInt("AJOURS"), modeRegRow.getInt("LENJOUR"), dFacture);
map.put("FactureDateEcheance", dateFormat.format(dateEch));
facturesNumero.add(foreign.getString("NUMERO"));
facturesRef.add(foreign.getString("NOM"));
facturesDate.add(dateFormat.format((Date) foreign.getObject("DATE")));
}
map.put("FactureNumero", CollectionUtils.join(facturesNumero, ","));
map.put("FactureReference", CollectionUtils.join(facturesRef, ","));
map.put("FactureDate", CollectionUtils.join(facturesDate, ","));
map.put("FacturesDetails", CollectionUtils.join(facturesDetails, "\n"));
map.put("FactureTotal", GestionDevise.currencyToString(lTotal.longValue(), true));
map.put("FactureRestant", GestionDevise.currencyToString(lRestant.longValue(), true));
map.put("FactureVerse", GestionDevise.currencyToString(lVerse.longValue(), true));
map.put("FactureDate", dateFormat.format((Date) rowFacture.getObject("DATE")));
 
Date dFacture = (Date) rowFacture.getObject("DATE");
SQLRow modeRegRow = rowFacture.getForeignRow("ID_MODE_REGLEMENT");
Date dateEch = ModeDeReglementSQLElement.calculDate(modeRegRow.getInt("AJOURS"), modeRegRow.getInt("LENJOUR"), dFacture);
map.put("FactureDateEcheance", dateFormat.format(dateEch));
map.put("message", "");
return map;
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/quote/component/DevisSQLComponent.java
1277,8 → 1277,16
rowVals.put("ID_TAXE_FRAIS_DOCUMENT", taxeDefault.getID());
}
if (getTable().getFieldsName().contains("DATE_VALIDITE")) {
 
Calendar cal = Calendar.getInstance();
cal.add(Calendar.MONTH, 1);
 
int jours = SQLPreferences.getMemCached(getTable().getDBRoot()).getInt(GestionCommercialeGlobalPreferencePanel.DEVIS_VALIDITE_JOURS, 30);
if (jours % 30 == 0) {
cal.add(Calendar.MONTH, jours / 30);
} else {
cal.add(Calendar.DAY_OF_YEAR, jours);
}
 
rowVals.put("DATE_VALIDITE", new java.sql.Date(cal.getTimeInMillis()));
}
return rowVals;
1380,24 → 1388,10
 
@Override
public void select(final SQLRowAccessor r) {
if (r == null || r.getIDNumber() == null)
super.select(r);
else {
System.err.println(r);
final SQLRowValues rVals = r.asRowValues().deepCopy();
final SQLRowValues vals = new SQLRowValues(r.getTable());
vals.load(rVals, createSet("ID_CLIENT"));
vals.setID(rVals.getID());
System.err.println("Select CLIENT");
 
super.select(vals);
rVals.remove("ID_CLIENT");
super.select(rVals);
}
 
// super.select(r);
if (r != null) {
this.table.insertFrom("ID_DEVIS", r.getID());
this.table.getRowValuesTable().clear();
this.table.getRowValuesTable().insertFrom(r);
// this.radioEtat.setVisible(r.getID() > getTable().getUndefinedID());
if (getTable().contains("SITE_DIFF"))
setSiteEnabled(r.getBoolean("SITE_DIFF"), Type_Diff.SITE);
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/quote/element/DevisSQLElement.java
674,7 → 674,7
@Override
protected synchronized void _initTableSource(final SQLTableModelSource table) {
super._initTableSource(table);
 
addCommercialFilter(table, getTable().getField("ID_COMMERCIAL"));
final BaseSQLTableModelColumn colAdrLiv = new BaseSQLTableModelColumn("Adresse de livraison", String.class) {
 
@Override
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/quote/action/ListeDesElementsDevisAction.java
56,7 → 56,7
c.anchor = GridBagConstraints.EAST;
c.fill = GridBagConstraints.NONE;
 
listeAddPanel.getListe().getRequest().setWhere(new Where(element.getTable().getField("ID_DEVIS"), ">", 1));
listeAddPanel.getListe().getRequest().putWhere("Undef", new Where(element.getTable().getField("ID_DEVIS"), ">", 1));
List<SQLField> l = new ArrayList<SQLField>();
l.add(element.getTable().getField("T_PV_HT"));
l.add(element.getTable().getField("T_PV_TTC"));
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/quote/ui/ListeDesDevisPanel.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
317,7 → 317,7
}
if (idFilter > 1) {
Where wAttente = new Where(this.eltDevis.getTable().getField("ID_ETAT_DEVIS"), "=", idFilter);
lAttente.getReq().setWhere(wAttente);
lAttente.getReq().putWhere("ETAT", wAttente);
} else {
lAttente.getColumns().add(new BaseSQLTableModelColumn("Etat", String.class) {
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/BatchHistoryPDF.java
New file
0,0 → 1,366
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.element;
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.core.finance.accounting.report.GrandLivrePDF;
import org.openconcerto.sql.model.DBRoot;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.Where;
import org.openconcerto.utils.StringUtils;
 
import java.awt.Color;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.text.DateFormat;
import java.text.DecimalFormat;
import java.text.DecimalFormatSymbols;
import java.util.Calendar;
import java.util.Collection;
import java.util.Date;
import java.util.Iterator;
import java.util.List;
import java.util.Locale;
 
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
import org.apache.pdfbox.pdmodel.font.PDType1Font;
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject;
 
public class BatchHistoryPDF {
 
private final DateFormat dateFormatEcr = DateFormat.getDateInstance(DateFormat.SHORT);
private final SQLRow rowSociete;
 
public static final String TEMPLATE_ID = "BatchHistory";
public static final String TEMPLATE_PROPERTY_NAME = "LocationGrandLivre";
private static final int LINE_HEIGHT = 10;
private static final float COL_1_SIZE = 100;
private static final float COL_2_SIZE = 35;
private static final float COL_3_SIZE = 375;
 
private static final float COL_1_X = 40;
private static final float COL_2_X = COL_1_X + COL_1_SIZE;
private static final float COL_3_X = COL_2_X + COL_2_SIZE;
 
private final DecimalFormat decimalFormat = new DecimalFormat("#,##0.00", DecimalFormatSymbols.getInstance(Locale.FRANCE));
private final SQLRowAccessor rowLot;
 
public BatchHistoryPDF(ComptaPropsConfiguration conf, SQLRowAccessor rowLot) {
this.rowSociete = conf.getRowSociete();
final DBRoot b = conf.getRootSociete();
this.rowLot = rowLot;
}
 
public void getGeneratedPDFFile(File f) throws IOException {
 
int y = 0;
final String companyName = this.rowSociete.getString("TYPE") + " " + this.rowSociete.getString("NOM");
 
final List<SQLRowValues> fetchLivraisonReception = fetchLivraisonReception(rowLot);
final SQLRowValues sqlRowValuesFetched = fetchLivraisonReception.get(0);
final Collection<SQLRowValues> receptionRows = sqlRowValuesFetched.getReferentRows(rowLot.getTable().getTable("LOT_RECEPTION"));
final Collection<SQLRowValues> livraisonRows = sqlRowValuesFetched.getReferentRows(rowLot.getTable().getTable("LOT_LIVRAISON"));
try (PDDocument doc = new PDDocument()) {
PDPageContentStream contents = null;
final int size = receptionRows.size();
final Iterator<SQLRowValues> iterator = receptionRows.iterator();
 
final PDPage page = new PDPage(PDRectangle.A4);
doc.addPage(page);
if (contents != null) {
contents.close();
}
contents = new PDPageContentStream(doc, page);
y = drawHeader(contents, companyName, sqlRowValuesFetched);
 
y -= 51;
contents.beginText();
contents.setFont(PDType1Font.HELVETICA, 12);
contents.newLineAtOffset(40, y);
contents.showText("Réception");
contents.endText();
 
y = drawTableHeader(contents, y, "FOURNISSEURS");
 
for (int i = 0; i < size; i++) {
 
final SQLRowValues rowRecep = iterator.next();
 
y = drawTAbleLine(contents, y, rowRecep);
 
}
 
y -= 68;
contents.beginText();
contents.setFont(PDType1Font.HELVETICA, 12);
contents.newLineAtOffset(40, y);
contents.showText("Livraison");
contents.endText();
 
y = drawTableHeader(contents, y, "CLIENTS");
 
final int sizeLivraison = livraisonRows.size();
final Iterator<SQLRowValues> iteratorLivraison = livraisonRows.iterator();
 
for (int i = 0; i < sizeLivraison; i++) {
 
final SQLRowValues rowLivraison = iteratorLivraison.next();
 
y = drawTAbleLine(contents, y, rowLivraison);
 
}
 
if (contents != null) {
contents.close();
}
 
// Header avec numéro de page
final InputStream sImage = GrandLivrePDF.class.getResourceAsStream("OpenConcerto_2000px.png");
final ByteArrayOutputStream bOut = new ByteArrayOutputStream();
final byte[] buf = new byte[8192];
int length;
while ((length = sImage.read(buf)) > 0) {
bOut.write(buf, 0, length);
}
sImage.close();
bOut.close();
 
final float ratio = 20;
final int pageCount = doc.getNumberOfPages();
for (int index = 0; index < pageCount; index++) {
final PDPage currentPage = doc.getPage(index);
contents = new PDPageContentStream(doc, currentPage, PDPageContentStream.AppendMode.APPEND, true, true);
if (index == 0 || index == pageCount - 1) {
final PDImageXObject pdImage = PDImageXObject.createFromByteArray(doc, bOut.toByteArray(), "openconcerto.png");
final float h = pdImage.getHeight() / ratio;
contents.drawImage(pdImage, 40, 10, pdImage.getWidth() / ratio, h);
}
contents.beginText();
contents.setFont(PDType1Font.HELVETICA, 10);
contents.newLineAtOffset(250, 20);
contents.showText(StringUtils.cleanPDFString("Edition du " + this.dateFormatEcr.format(new Date())));
contents.endText();
 
contents.beginText();
contents.setFont(PDType1Font.HELVETICA, 10);
contents.newLineAtOffset(500, 20);
contents.showText("Page " + (index + 1) + " / " + pageCount);
contents.endText();
contents.close();
}
 
doc.save(f);
}
 
}
 
private int drawTAbleLine(PDPageContentStream contents, int y, SQLRowAccessor r) throws IOException {
y -= LINE_HEIGHT;
 
contents.setFont(PDType1Font.HELVETICA, 7);
final DateFormat format = DateFormat.getDateInstance(DateFormat.SHORT);
 
final String tiers, date, doc;
// TIERS, DATE, N°DOC,
if (r.getTable().getName().equals("LOT_LIVRAISON")) {
final SQLRowAccessor bl = r.getForeign("ID_BON_DE_LIVRAISON_ELEMENT").getForeign("ID_BON_DE_LIVRAISON");
final SQLRowAccessor client = bl.getForeign("ID_CLIENT");
 
tiers = client.getString("NOM");
date = format.format(bl.getDate("DATE").getTime());
doc = bl.getString("NUMERO");
} else {
final SQLRowAccessor br = r.getForeign("ID_BON_RECEPTION_ELEMENT").getForeign("ID_BON_RECEPTION");
final SQLRowAccessor four = br.getForeign("ID_FOURNISSEUR");
 
tiers = four.getString("NOM");
date = format.format(br.getDate("DATE").getTime());
doc = br.getString("NUMERO");
}
 
contents.beginText();
contents.newLineAtOffset(COL_1_X, y);
contents.showText(StringUtils.cleanPDFString(doc));
contents.endText();
contents.beginText();
contents.newLineAtOffset(COL_2_X, y);
contents.showText(StringUtils.cleanPDFString(date));
contents.endText();
contents.beginText();
contents.newLineAtOffset(COL_3_X, y);
contents.showText(StringUtils.cleanPDFString(tiers));
contents.endText();
 
// if (r.getDate("DLUO") != null) {
// drawRightAlign(contents, COL_1_X, y, COL_1_SIZE - 5,
// this.dateFormatEcr.format(r.getDate("DLUO")));
// }
// if (r.getDate("DLC") != null) {
// drawRightAlign(contents, COL_2_X, y, COL_2_SIZE - 5,
// this.dateFormatEcr.format(r.getDate("DLC")));
// }
//
// if (r.getString("NUMERO_SERIE") != null && r.getString("NUMERO_SERIE").trim().length() >
// 0) {
// contents.beginText();
// contents.newLineAtOffset(COL_3_X, y);
// contents.showText( StringUtils.cleanPDFString(r.getString("NUMERO_SERIE")));
// contents.endText();
// }
// if (r.getString("NUMERO_LOT") != null && r.getString("NUMERO_LOT").trim().length() > 0) {
// contents.beginText();
// contents.newLineAtOffset(COL_4_X, y);
// contents.showText( StringUtils.cleanPDFString(r.getString("NUMERO_LOT")));
// contents.endText();
// }
// contents.beginText();
// contents.newLineAtOffset(COL_4_X, y);
// contents.showText(StringUtils.limitLength( StringUtils.cleanPDFString(libelle), 66));
// contents.endText();
//
// drawRightAlign(contents, COL_5_X, y, COL_5_SIZE, this.decimalFormat.format(debit));
// drawRightAlign(contents, COL_6_X, y, COL_6_SIZE, this.decimalFormat.format(credit));
// drawRightAlign(contents, COL_7_X, y, COL_7_SIZE, this.decimalFormat.format(solde));
 
contents.setLineWidth(0.5f);
contents.setStrokingColor(Color.LIGHT_GRAY);
contents.moveTo(COL_1_X - 4, y - 2f);
contents.lineTo(COL_3_X + 4 + COL_3_SIZE, y - 2f);
contents.stroke();
 
return y;
}
 
private void drawRightAlign(PDPageContentStream contents, float x, float y, float width, String text) throws IOException {
contents.beginText();
final float w = PDType1Font.HELVETICA.getStringWidth(StringUtils.cleanPDFString(text)) / 1000.0f * 7f;
contents.newLineAtOffset(x + width - w, y);
contents.showText(StringUtils.cleanPDFString(text));
contents.endText();
}
 
private int drawHeader(PDPageContentStream contents, String companyName, SQLRowAccessor rLot) throws IOException {
int y = 795;
contents.beginText();
contents.setFont(PDType1Font.HELVETICA_BOLD, 14);
contents.newLineAtOffset(40, y);
contents.showText(StringUtils.cleanPDFString(companyName.toUpperCase()));
contents.endText();
y -= 17;
 
final SQLRowAccessor foreign = rLot.getForeign("ID_STOCK").getForeign("ID_ARTICLE");
 
y = drawLine(contents, "Article " + foreign.getString("NOM"), y);
y = drawLine(contents, "Code : " + foreign.getString("CODE"), y);
 
DateFormat format = DateFormat.getDateInstance(DateFormat.SHORT);
StringBuilder res = new StringBuilder();
final Calendar dluo = rLot.getDate("DLUO");
final Calendar dlc = rLot.getDate("DLC");
final String lot = rLot.getString("NUMERO_LOT");
final String serie = rLot.getString("NUMERO_SERIE");
 
if (serie != null && serie.trim().length() > 0) {
y = drawLine(contents, "Numéro Série : " + serie, y);
}
if (lot != null && lot.trim().length() > 0) {
y = drawLine(contents, "Numéro Lot : " + lot, y);
}
if (dlc != null) {
y = drawLine(contents, "DLC : " + format.format(dlc.getTime()), y);
}
if (dluo != null) {
y = drawLine(contents, "DLUO : " + format.format(dluo.getTime()), y);
}
 
return y;
 
}
 
private int drawLine(PDPageContentStream contents, String text, int y) throws IOException {
y -= 17;
contents.beginText();
contents.setFont(PDType1Font.HELVETICA, 12);
contents.newLineAtOffset(40, y);
contents.showText(StringUtils.cleanPDFString(text));
contents.endText();
return y;
}
 
private int drawTableHeader(PDPageContentStream contents, int y, String tiers) throws IOException {
 
y -= 20;
contents.setFont(PDType1Font.HELVETICA_BOLD, 7);
 
contents.beginText();
contents.newLineAtOffset(COL_1_X + 5, y);
contents.showText("NUMERO DOCUMENT");
contents.endText();
 
contents.beginText();
contents.newLineAtOffset(COL_2_X, y);
contents.showText("DATE");
contents.endText();
 
contents.beginText();
contents.newLineAtOffset(COL_3_X, y);
contents.showText(tiers);
contents.endText();
 
y -= 4;
contents.setStrokingColor(Color.BLACK);
contents.setLineWidth(1f);
contents.moveTo(COL_1_X - 4, y);
contents.lineTo(COL_3_X + COL_3_SIZE + 4, y);
contents.stroke();
 
return y;
}
 
private List<SQLRowValues> fetchLivraisonReception(SQLRowAccessor rowLot) {
final SQLRowValues vals = new SQLRowValues(rowLot.getTable());
vals.setAllToNull();
final SQLRowValues putRowValuesARticle = vals.putRowValues("ID_STOCK").putRowValues("ID_ARTICLE");
putRowValuesARticle.putNulls("CODE", "NOM");
putRowValuesARticle.putRowValues("ID_ARTICLE_DECLINAISON_COULEUR").putNulls("NOM");
putRowValuesARticle.putRowValues("ID_ARTICLE_DECLINAISON_TAILLE").putNulls("NOM");
 
final SQLRowValues valsReception = new SQLRowValues(rowLot.getTable().getTable("LOT_RECEPTION"));
valsReception.setAllToNull();
valsReception.put("ID_LOT", vals);
final SQLRowValues rowValsBR = valsReception.putRowValues("ID_BON_RECEPTION_ELEMENT").putRowValues("ID_BON_RECEPTION");
rowValsBR.putNulls("NUMERO", "DATE");
rowValsBR.putRowValues("ID_FOURNISSEUR").putNulls("CODE", "NOM");
 
final SQLRowValues valsLivraison = new SQLRowValues(rowLot.getTable().getTable("LOT_LIVRAISON"));
valsLivraison.setAllToNull();
valsLivraison.put("ID_LOT", vals);
final SQLRowValues rowValsBL = valsLivraison.putRowValues("ID_BON_DE_LIVRAISON_ELEMENT").putRowValues("ID_BON_DE_LIVRAISON");
rowValsBL.putNulls("NUMERO", "DATE");
rowValsBL.putRowValues("ID_CLIENT").putNulls("CODE", "NOM");
 
SQLRowValuesListFetcher fetcher = SQLRowValuesListFetcher.create(vals);
 
return fetcher.fetch(new Where(rowLot.getTable().getKey(), "=", rowLot.getID()));
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/ListeDesLotsAction.java
16,10 → 16,14
import org.openconcerto.erp.action.CreateFrameAbstractAction;
import org.openconcerto.sql.element.SQLElementDirectory;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLSelectJoin;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.view.IListFrame;
import org.openconcerto.sql.view.ListeAddPanel;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.SQLTableModelSource;
import org.openconcerto.utils.cc.ITransformer;
 
import javax.swing.JFrame;
 
34,8 → 38,23
 
@Override
public JFrame createFrame() {
final SQLTableModelSource tableSource = dir.getElement(LotSQLElement.class).createTableSource();
final LotSQLElement element = dir.getElement(LotSQLElement.class);
final SQLTableModelSource tableSource = element.createTableSource();
if (selectedRowAccessor != null) {
tableSource.getReq().setSelectTransf(new ITransformer<SQLSelect, SQLSelect>() {
 
@Override
public SQLSelect transformChecked(SQLSelect input) {
final SQLSelectJoin join = input.getJoin(element.getTable().getField("ID_STOCK"));
input.setWhere(new Where(join.getJoinedTable().getField("ID_ARTICLE"), "=", selectedRowAccessor.getID()));
return input;
}
});
}
IListFrame frame = new IListFrame(new ListeAddPanel(tableSource.getElem(), new IListe(tableSource)));
frame.getPanel().setAddVisible(false);
frame.getPanel().setModifyVisible(false);
frame.getPanel().setDeleteVisible(false);
return frame;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/UniteVenteArticleSQLElement.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
30,7 → 30,14
public class UniteVenteArticleSQLElement extends ComptaSQLConfElement {
 
public static final int A_LA_PIECE = 2;
public static final int METRE = 3;
public static final int M2 = 4;
public static final int M3 = 5;
public static final int LITRE = 6;
public static final int KG = 7;
public static final int HEURE = 8;
public static final int JOURE = 9;
public static final int MOIS = 10;
 
public UniteVenteArticleSQLElement() {
super("UNITE_VENTE", "une unité de vente", "unité de vente");
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/LotSQLElement.java
13,19 → 13,85
package org.openconcerto.erp.core.sales.product.element;
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.config.Gestion;
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.finance.accounting.ui.ImpressionGrandLivrePanel;
import org.openconcerto.erp.core.sales.product.model.BatchQuantity;
import org.openconcerto.erp.core.sales.product.model.ProductComponent;
import org.openconcerto.erp.core.supplychain.stock.element.DepotStockSQLElement;
import org.openconcerto.sql.element.BaseSQLComponent;
import org.openconcerto.sql.element.SQLComponent;
import org.openconcerto.sql.model.SQLInsert;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLSelectJoin;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.SQLUpdate;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.request.UpdateBuilder;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.RowValuesTableModel;
import org.openconcerto.sql.view.list.IListeAction.IListeEvent;
import org.openconcerto.sql.view.list.action.SQLRowValuesAction.PredicateRowAction;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.ListMap;
import org.openconcerto.utils.cc.ITransformer;
import org.openconcerto.utils.checks.ValidState;
 
import java.awt.GridBagLayout;
import java.io.File;
import java.io.IOException;
import java.math.BigDecimal;
import java.sql.SQLException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
 
import javax.swing.JFileChooser;
import javax.swing.SwingUtilities;
 
public class LotSQLElement extends ComptaSQLConfElement {
 
public LotSQLElement() {
super("LOT", "un lot", "lots");
 
PredicateRowAction action = new PredicateRowAction(true, "batch.history.pdf.action",(le) -> {
JFileChooser chooser = new JFileChooser();
SimpleDateFormat df = new SimpleDateFormat("dd-MM-yyyy");
chooser.setSelectedFile(new File("BatchTracking " + le.getSelectedRow().getID() + "-" + df.format(new Date()) + ".pdf"));
int r = chooser.showSaveDialog(null);
if (r == JFileChooser.APPROVE_OPTION) {
BatchHistoryPDF pdf = new BatchHistoryPDF(ComptaPropsConfiguration.getInstanceCompta(), le.getSelectedRow());
final File file = chooser.getSelectedFile();
try {
pdf.getGeneratedPDFFile(file);
 
SwingUtilities.invokeLater(new Runnable() {
 
@Override
public void run() {
Gestion.openPDF(file);
}
});
} catch (IOException e) {
ExceptionHandler.handle("Erreur lors de la création du PDF", e);
}
}
});
action.setPredicate(IListeEvent.getSingleSelectionPredicate());
getRowValuesActions().add(action);
}
 
@Override
protected List<String> getListFields() {
52,6 → 118,13
}
 
@Override
public ListMap<String, String> getShowAs() {
ListMap<String, String> map = new ListMap<>();
map.add("ID_STOCK", "ID_DEPOT_STOCK");
return map;
}
 
@Override
public SQLComponent createComponent() {
return new BaseSQLComponent(this) {
 
63,8 → 136,414
};
}
 
public ValidState getValidStateOfRowValuesTable(RowValuesTableModel rowValuesTableModel, TypeLot type) {
for (int line = 0; line < rowValuesTableModel.getRowCount(); line++) {
final SQLRowValues rowValuesAt = rowValuesTableModel.getRowValuesAt(line);
final SQLRowAccessor nonEmptyForeign = rowValuesAt.getNonEmptyForeign("ID_ARTICLE");
if (nonEmptyForeign != null) {
final SQLRow asRowArticle = nonEmptyForeign.asRow();
final Boolean lotReq = asRowArticle.getBoolean("NUMERO_LOT_REQUIS");
final Boolean lotSerie = asRowArticle.getBoolean("NUMERO_SERIE_REQUIS");
final Boolean lotDLC = asRowArticle.getBoolean("DLC_REQUIS");
final Boolean lotDLUO = asRowArticle.getBoolean("DLUO_REQUIS");
if (lotReq || lotSerie) {
final Set<SQLRowValues> referentRows = rowValuesAt.getReferentRows(getTable().getTable(type.getTableLot()).getField("ID_" + type.getTableItems()));
List<SQLRowValues> lotRows = new ArrayList<>();
for (SQLRowValues sqlRowValues : referentRows) {
if (!sqlRowValues.contains("ARCHIVE") || !sqlRowValues.isArchived()) {
if (lotReq && sqlRowValues.getString("NUMERO_LOT").trim().length() == 0) {
return ValidState.create(false, "Ligne " + (line + 1) + " : lot sans référence!");
}
if (lotSerie && sqlRowValues.getString("NUMERO_SERIE").trim().length() == 0) {
return ValidState.create(false, "Ligne " + (line + 1) + " : numéro de série non renseigné!");
}
if (lotDLC && sqlRowValues.getDate("DLC") == null) {
return ValidState.create(false, "Ligne " + (line + 1) + " : DLC non renseignée!");
}
if (lotDLUO && sqlRowValues.getDate("DLUO") == null) {
return ValidState.create(false, "Ligne " + (line + 1) + " : DLUO non renseignée!");
}
 
lotRows.add(sqlRowValues);
 
}
}
if (lotRows.isEmpty()) {
return ValidState.create(false, "La ligne " + (line + 1) + " n'a aucun lot associé!");
}
}
 
}
}
return ValidState.getTrueInstance();
}
 
public void updateLotQuantiteFromLotItems(List<SQLRowValues> rowValues, TypeLot type) throws SQLException {
 
if (!rowValues.isEmpty()) {
final List<Integer> findOrCreateLot = findOrCreateLot(rowValues);
if (findOrCreateLot.size() != rowValues.size()) {
throw new IllegalArgumentException("La taille des lignes de bons [" + rowValues.size() + "] ne correspond pas à la liste des lots trouvés [" + findOrCreateLot.size() + "]");
}
List<String> updates = new ArrayList<>();
for (int index = 0; index < findOrCreateLot.size(); index++) {
UpdateBuilder builder = new UpdateBuilder(getTable());
builder.set("QUANTITE", getTable().getField("QUANTITE").getQuotedName() + (type == TypeLot.RECEPTION ? " + " : " - ") + rowValues.get(index).getBigDecimal("QUANTITE"));
builder.setWhere(new Where(getTable().getKey(), "=", findOrCreateLot.get(index)));
updates.add(builder.asString());
}
getTable().getDBSystemRoot().getDataSource().executeBatch(updates, true);
}
}
 
public void removeLotQuantiteFromLotItems(List<SQLRowValues> rowValuesLotReceptionOrLivraison, TypeLot type) throws SQLException {
 
if (!rowValuesLotReceptionOrLivraison.isEmpty()) {
final List<Integer> findOrCreateLot = findOrCreateLot(rowValuesLotReceptionOrLivraison);
if (findOrCreateLot.size() != rowValuesLotReceptionOrLivraison.size()) {
throw new IllegalArgumentException(
"La taille des lignes de bons [" + rowValuesLotReceptionOrLivraison.size() + "] ne correspond pas à la liste des lots trouvés [" + findOrCreateLot.size() + "]");
}
List<String> updates = new ArrayList<>();
for (int index = 0; index < findOrCreateLot.size(); index++) {
UpdateBuilder builder = new UpdateBuilder(getTable());
builder.set("QUANTITE",
getTable().getField("QUANTITE").getQuotedName() + (type == TypeLot.RECEPTION ? " - " : " + ") + rowValuesLotReceptionOrLivraison.get(index).getBigDecimal("QUANTITE"));
builder.setWhere(new Where(getTable().getKey(), "=", findOrCreateLot.get(index)));
updates.add(builder.asString());
}
getTable().getDBSystemRoot().getDataSource().executeBatch(updates, true);
}
}
 
/**
* Recherche des ids des lots qui correspondent avec le numero de serie et/ou le numero de lot
* des lignes de lot de reception/livraison passées en parametres
*
* @param rowValuesLotRecOrLiv
* @return
* @throws SQLException
*/
 
public List<Integer> findOrCreateLot(List<SQLRowValues> rowValuesLotRecOrLiv) throws SQLException {
 
final SQLTable tableItem;
if (rowValuesLotRecOrLiv.isEmpty()) {
return new ArrayList<>();
} else {
tableItem = rowValuesLotRecOrLiv.get(0).getTable();
}
 
// Récupération des numeros de lot et numeros de serie à retrouver
List<String> numeroLot = new ArrayList<>();
List<String> numeroSerie = new ArrayList<>();
for (SQLRowValues r : rowValuesLotRecOrLiv) {
if (r.isForeignEmpty("ID_LOT")) {
final String lot = r.getString("NUMERO_LOT");
final String serie = r.getString("NUMERO_SERIE");
if (lot.length() > 0) {
numeroLot.add(lot);
}
if (serie.length() > 0) {
numeroSerie.add(serie);
}
}
}
 
// Création d'une map pour faire la correspondance nuemro de lot / numero de serie avec une
// row LOT
SQLRowValues rowValsToFecth = new SQLRowValues(getTable());
rowValsToFecth.putNulls("DLC", "DLUO", "QUANTITE", "NUMERO_SERIE", "NUMERO_LOT");
rowValsToFecth.putRowValues("ID_STOCK").putNulls("ID_ARTICLE", "ID_DEPOT_STOCK");
 
SQLRowValuesListFetcher fetcher = SQLRowValuesListFetcher.create(rowValsToFecth);
final List<SQLRowValues> resultMatchLot = fetcher.fetch(Where.inValues(getTable().getField("NUMERO_LOT"), numeroLot).or(Where.inValues(getTable().getField("NUMERO_SERIE"), numeroSerie)));
Map<LotKey, SQLRowValues> mapLotSerie = new HashMap<>();
for (SQLRowValues sqlRowValues : resultMatchLot) {
final SQLRowAccessor foreignStock = sqlRowValues.getForeign("ID_STOCK");
LotKey key = new LotKey(foreignStock.getForeignID("ID_ARTICLE"), foreignStock.getForeignID("ID_DEPOT_STOCK"), sqlRowValues.getString("NUMERO_SERIE"), sqlRowValues.getString("NUMERO_LOT"));
mapLotSerie.put(key, sqlRowValues);
}
 
// Matching/Creation des Lots
List<Integer> idsLot = new ArrayList<>(rowValuesLotRecOrLiv.size());
List<SQLInsert> inserts = new ArrayList<>();
List<String> fieldsToCopy = Arrays.asList("DLC", "DLUO", "NUMERO_SERIE", "NUMERO_LOT");
for (int i = 0; i < rowValuesLotRecOrLiv.size(); i++) {
SQLRowValues rowVals = rowValuesLotRecOrLiv.get(i);
final int foreignIDDepot = rowVals.isForeignEmpty("ID_DEPOT_STOCK") ? DepotStockSQLElement.DEFAULT_ID : rowVals.getForeignID("ID_DEPOT_STOCK");
LotKey key = new LotKey(rowVals.getForeignID("ID_ARTICLE"), foreignIDDepot, rowVals.getString("NUMERO_SERIE"), rowVals.getString("NUMERO_LOT"));
 
if (!rowVals.isForeignEmpty("ID_LOT")) {
idsLot.add(rowVals.getForeignID("ID_LOT"));
} else if (mapLotSerie.containsKey(key)) {
idsLot.add(mapLotSerie.get(key).getID());
} else {
idsLot.add(null);
SQLInsert insert = new SQLInsert();
for (String f : fieldsToCopy) {
insert.add(getTable().getField(f), rowVals.getObject(f));
}
insert.add(getTable().getField("QUANTITE"), BigDecimal.ZERO);
String fieldForeignBonItem = tableItem.getName().equals("LOT_RECEPTION") ? "ID_BON_RECEPTION_ELEMENT" : "ID_BON_LIVRAISON_ELEMENT";
final SQLRowAccessor bonTiem = rowVals.getForeign(fieldForeignBonItem);
final SQLRowAccessor foreignArt = bonTiem.getForeign("ID_ARTICLE");
ProductComponent comp = ProductComponent.createFromRowArticle(foreignArt, bonTiem);
stock(comp);
insert.add(getTable().getField("ID_STOCK"), comp.getStock().getID());
inserts.add(insert);
 
}
}
if (!inserts.isEmpty()) {
List<SQLUpdate> updates = new ArrayList<>();
final List<Number> executeSimilarInserts = SQLInsert.executeSimilarInserts(getTable().getDBSystemRoot(), inserts, true);
int index = 0;
for (int i = 0; i < idsLot.size(); i++) {
Integer id = idsLot.get(i);
if (id == null) {
final int insertedId = executeSimilarInserts.get(index).intValue();
idsLot.set(i, insertedId);
SQLUpdate update = new SQLUpdate(new Where(tableItem.getKey(), "=", rowValuesLotRecOrLiv.get(i).getID()));
update.add(tableItem.getField("ID_LOT"), insertedId);
updates.add(update);
index++;
}
}
if (!updates.isEmpty()) {
SQLUpdate.executeMultipleWithBatch(tableItem.getDBSystemRoot(), updates);
}
}
return idsLot;
}
 
public List<SQLRowValues> createLotLivraison(List<BatchQuantity> l, SQLRowValues refBLRowItem) {
 
Map<Integer, SQLRowValues> rowValsExists = new HashMap<>();
final Set<SQLRowValues> referentRows = refBLRowItem.getReferentRows(getTable().getTable("LOT_LIVRAISON").getField("ID_BON_DE_LIVRAISON_ELEMENT"));
for (SQLRowValues sqlRowValues : referentRows) {
rowValsExists.put(sqlRowValues.getForeignID("ID_LOT"), sqlRowValues);
}
 
List<Integer> idBatchsNotExisting = new ArrayList<>();
Set<Integer> idBatchsExisting = new HashSet<>();
for (BatchQuantity batchQuantity : l) {
final int idBatch = batchQuantity.getIdBatch();
if (!rowValsExists.containsKey(idBatch)) {
idBatchsNotExisting.add(idBatch);
} else {
idBatchsExisting.add(idBatch);
}
}
// On retire les lots qui ne sont plus référencés
final Set<Integer> keySet = new HashSet<Integer>(rowValsExists.keySet());
keySet.removeAll(idBatchsExisting);
for (Integer integer : keySet) {
rowValsExists.get(integer).put("ARCHIVE", 1);
}
 
SQLRowValues rowValsToFetch = new SQLRowValues(getTable());
rowValsToFetch.putNulls(getTable().getFieldsName());
final SQLRowValues putRowValues = rowValsToFetch.putRowValues("ID_STOCK");
putRowValues.putNulls("ID_DEPOT_STOCK");
putRowValues.putRowValues("ID_ARTICLE").putNulls("NOM");
final List<SQLRowValues> fetch = SQLRowValuesListFetcher.create(rowValsToFetch).fetch(Where.inValues(getTable().getKey(), idBatchsNotExisting));
Map<Integer, SQLRowValues> mapLot = new HashMap<>();
for (SQLRowValues sqlRowValues : fetch) {
mapLot.put(sqlRowValues.getID(), sqlRowValues);
}
 
List<SQLRowValues> items = new ArrayList<>();
for (BatchQuantity batchQuantity : l) {
final int idBatch = batchQuantity.getIdBatch();
final BigDecimal quantity = batchQuantity.getQuantity();
final SQLRowValues rowVals;
if (rowValsExists.containsKey(idBatch)) {
rowVals = rowValsExists.get(idBatch);
} else {
rowVals = new SQLRowValues(getTable().getTable("LOT_LIVRAISON"));
final SQLRowValues rLot = mapLot.get(idBatch);
final SQLRowAccessor foreignStock = rLot.getForeign("ID_STOCK");
final SQLRowAccessor foreignArticle = foreignStock.getForeign("ID_ARTICLE");
rowVals.put("ARTICLE", foreignArticle.getString("NOM"));
rowVals.put("ID_ARTICLE", foreignArticle.getID());
rowVals.put("ID_BON_DE_LIVRAISON_ELEMENT", refBLRowItem);
rowVals.put("ID_DEPOT_STOCK", foreignStock.getForeignID("ID_DEPOT_STOCK"));
rowVals.put("ID_LOT", idBatch);
rowVals.put("NUMERO_LOT", rLot.getObject("NUMERO_LOT"));
rowVals.put("DLC", rLot.getObject("DLC"));
rowVals.put("DLUO", rLot.getObject("DLUO"));
rowVals.put("NUMERO_SERIE", rLot.getObject("NUMERO_SERIE"));
}
rowVals.put("QUANTITE", quantity);
items.add(rowVals);
}
return items;
}
 
public List<BatchQuantity> createBatchQuantity(List<SQLRowValues> lotLivraisonItems) throws SQLException {
 
final List<Integer> findOrCreateLot = findOrCreateLot(lotLivraisonItems);
List<BatchQuantity> l = new ArrayList<>();
for (int index = 0; index < findOrCreateLot.size(); index++) {
final Integer idLot = findOrCreateLot.get(index);
final SQLRowValues lotItem = lotLivraisonItems.get(index);
l.add(new BatchQuantity(idLot, lotItem.getBigDecimal("QUANTITE"), BigDecimal.ZERO));
}
return l;
}
 
public void updateLotQuantiteFromBRItems(List<SQLRowValues> rowValuesBRItems) throws SQLException {
 
updateLotQuantiteFromLotItems(fetchLotItem(SQLRow.getIDs(rowValuesBRItems), TypeLot.RECEPTION), TypeLot.RECEPTION);
 
}
 
public void removeLotQuantiteFromBR(List<SQLRowValues> rowValuesBR) throws SQLException {
 
removeLotQuantiteFromLotItems(fetchLotItemsFromBonItems(SQLRow.getIDs(rowValuesBR), TypeLot.RECEPTION), TypeLot.RECEPTION);
 
}
 
public void removeLotQuantiteFromBR(Collection<Integer> idsBR) throws SQLException {
 
removeLotQuantiteFromLotItems(fetchLotItemsFromBonItems(idsBR, TypeLot.RECEPTION), TypeLot.RECEPTION);
 
}
 
public void updateLotQuantiteFromBLItems(List<SQLRowValues> rowValuesBLItems) throws SQLException {
 
updateLotQuantiteFromLotItems(fetchLotItem(SQLRow.getIDs(rowValuesBLItems), TypeLot.LIVRAISON), TypeLot.LIVRAISON);
 
}
 
public void removeLotQuantiteFromBL(List<SQLRowValues> rowValuesBL) throws SQLException {
 
removeLotQuantiteFromLotItems(fetchLotItemsFromBonItems(SQLRow.getIDs(rowValuesBL), TypeLot.LIVRAISON), TypeLot.LIVRAISON);
 
}
 
public void removeLotQuantiteFromBL(Collection<Integer> idsBL) throws SQLException {
 
removeLotQuantiteFromLotItems(fetchLotItemsFromBonItems(idsBL, TypeLot.LIVRAISON), TypeLot.LIVRAISON);
 
}
 
public enum TypeLot {
RECEPTION("LOT_RECEPTION", "BON_RECEPTION_ELEMENT", "BON_RECEPTION"), LIVRAISON("LOT_LIVRAISON", "BON_DE_LIVRAISON_ELEMENT", "BON_DE_LIVRAISON");
 
private final String tableLot, tableItems, tableRootItems;
 
private TypeLot(String tableLot, String tableItems, String tableRootItems) {
this.tableLot = tableLot;
this.tableItems = tableItems;
this.tableRootItems = tableRootItems;
}
 
public String getTableItems() {
return tableItems;
}
 
public String getTableLot() {
return tableLot;
}
 
public String getTableRootItems() {
return tableRootItems;
}
};
 
/**
* Récupération des lignes de lotReception/LotLivraison depuis une liste de br/bl items
*
* @param idsBRItem
* @return
* @throws SQLException
*/
public List<SQLRowValues> fetchLotItem(Collection<Number> idsBRorBLItem, TypeLot type) throws SQLException {
 
final SQLTable brItemTable = getTable().getTable(type.getTableItems());
SQLRowValues rowValsBRItem = new SQLRowValues(brItemTable);
rowValsBRItem.putRowValues("ID_ARTICLE").putNulls("ID_DEPOT_STOCK");
rowValsBRItem.putNulls("ID_DEPOT_STOCK");
final SQLTable lotReceipttable = getTable().getTable(type.getTableLot());
SQLRowValues rowValsLotReceipt = new SQLRowValues(lotReceipttable);
rowValsLotReceipt.putNulls("DLC", "DLUO", "QUANTITE", "NUMERO_SERIE", "NUMERO_LOT", "ID_ARTICLE", "ID_DEPOT_STOCK", "ID_LOT").put("ID_" + type.getTableItems(), rowValsBRItem);
final SQLRowValuesListFetcher fetcher = SQLRowValuesListFetcher.create(rowValsLotReceipt);
fetcher.setSelTransf(new ITransformer<SQLSelect, SQLSelect>() {
@Override
public SQLSelect transformChecked(SQLSelect input) {
final SQLSelectJoin join = input.getJoin(lotReceipttable.getField("ID_" + type.getTableItems()));
input.setWhere(Where.inValues(join.getJoinedTable().getKey(), idsBRorBLItem));
return input;
}
});
 
return fetcher.fetch();
 
}
 
/**
* Récupération des lignes de lotReception depuis une liste de br
*
* @param idsBRItem
* @return
* @throws SQLException
*/
public List<SQLRowValues> fetchLotItemsFromBonItems(Collection<? extends Number> idsBRorBL, TypeLot type) throws SQLException {
 
final SQLTable brItemTable = getTable().getTable(type.getTableItems());
SQLRowValues rowValsBRItem = new SQLRowValues(brItemTable);
rowValsBRItem.putRowValues("ID_ARTICLE").putNulls("ID_DEPOT_STOCK");
rowValsBRItem.putNulls("ID_DEPOT_STOCK");
final SQLTable lotReceipttable = getTable().getTable(type.getTableLot());
SQLRowValues rowValsLotReceipt = new SQLRowValues(lotReceipttable);
rowValsLotReceipt.putNulls("DLC", "DLUO", "QUANTITE", "NUMERO_SERIE", "NUMERO_LOT", "ID_LOT", "ID_ARTICLE", "ID_DEPOT_STOCK").put("ID_" + type.getTableItems(), rowValsBRItem);
final SQLRowValuesListFetcher fetcher = SQLRowValuesListFetcher.create(rowValsLotReceipt);
fetcher.setSelTransf(new ITransformer<SQLSelect, SQLSelect>() {
@Override
public SQLSelect transformChecked(SQLSelect input) {
final SQLSelectJoin join = input.getJoin(lotReceipttable.getField("ID_" + type.getTableItems()));
input.setWhere(Where.inValues(join.getJoinedTable().getField("ID_" + type.getTableRootItems()), idsBRorBL));
return input;
}
});
 
return fetcher.fetch();
 
}
 
public void stock(ProductComponent comp) {
comp.getStock();
}
 
@Override
protected String createCode() {
return createCodeOfPackage() + ".batch";
}
 
class LotKey {
private final Integer idArticle, idDepot;
private final String serie, lot;
 
public LotKey(final Integer idArticle, final Integer idDepot, final String serie, final String lot) {
 
this.idArticle = idArticle;
this.idDepot = idDepot;
this.serie = serie;
this.lot = lot;
}
 
@Override
public int hashCode() {
return this.idArticle.hashCode() ^ this.idDepot.hashCode() ^ this.serie.hashCode() ^ this.lot.hashCode();
}
 
@Override
public boolean equals(Object obj) {
 
return obj instanceof LotKey && ((LotKey) obj).idArticle.equals(idArticle) && ((LotKey) obj).idDepot.equals(idDepot) && ((LotKey) obj).serie.equals(serie)
&& ((LotKey) obj).lot.equals(lot);
}
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/ReferenceArticleSQLElement.java
23,11 → 23,13
import org.openconcerto.erp.core.reports.history.ui.HistoriqueArticleFrame;
import org.openconcerto.erp.core.sales.product.action.InitializeStockPanel;
import org.openconcerto.erp.core.sales.product.action.InventairePanel;
import org.openconcerto.erp.core.sales.product.action.TransfertStockFromArticlePanel;
import org.openconcerto.erp.core.sales.product.component.ReferenceArticleSQLComponent;
import org.openconcerto.erp.core.sales.product.model.ProductComponent;
import org.openconcerto.erp.core.supplychain.stock.action.ListeDesMouvementsStockAction;
import org.openconcerto.erp.core.supplychain.stock.element.ComposedItemStockUpdater;
import org.openconcerto.erp.core.supplychain.stock.element.DepotStockSQLElement;
import org.openconcerto.erp.core.supplychain.stock.element.StockConsultPanel;
import org.openconcerto.erp.core.supplychain.stock.element.StockItem;
import org.openconcerto.erp.core.supplychain.stock.element.StockItem.TypeStockMouvement;
import org.openconcerto.erp.generationDoc.gestcomm.FicheArticleXmlSheet;
46,6 → 48,7
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowListRSH;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.Where;
87,8 → 90,10
import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
 
import javax.swing.AbstractAction;
106,6 → 111,7
public static final int AU_POID_METRECARRE = 4;
public static final int A_LA_PIECE = 5;
public static final int AU_METRE_LARGEUR = 6;
public static final int AU_KILO = 7;
private static final int PRIX_HA = 1;
private static final int PRIX_VT = 2;
protected PredicateRowAction stock;
169,7 → 175,47
}
}, true, false).setPredicate(ListEvent.getNonEmptySelectionPredicate());
getRowActions().add(actionConvVirtuel);
 
RowAction actionTransfert = new RowAction(new AbstractAction("Transfert de stock") {
 
@Override
public void actionPerformed(ActionEvent e) {
 
final SQLRowAccessor selectedRowAccessor = IListe.get(e).getSelectedRowAccessor().fetchNewRow(false);
PanelFrame frame = new PanelFrame(new TransfertStockFromArticlePanel(ComptaPropsConfiguration.getInstance(), selectedRowAccessor, null), "Transfert de stock");
FrameUtil.showPacked(frame);
frame.setLocationRelativeTo(IListe.get(e));
}
}, true, false) {
 
@Override
public boolean enabledFor(ListEvent evt) {
return evt.getSelectedRowAccessors().size() == 1 && evt.getSelectedRowAccessors().get(0).getBoolean("GESTION_STOCK");
}
};
getRowActions().add(actionTransfert);
 
RowAction actionStockShow = new RowAction(new AbstractAction("Consulter le stock") {
 
@Override
public void actionPerformed(ActionEvent e) {
 
final StockConsultPanel p = new StockConsultPanel(ReferenceArticleSQLElement.this, IListe.get(e).getSelectedRowAccessor());
// p.load(IListe.get(e).getSelectedRowAccessor());
PanelFrame frame = new PanelFrame(p, "Consultation du stock");
FrameUtil.showPacked(frame);
frame.setLocationRelativeTo(IListe.get(e));
}
}, true, false) {
 
@Override
public boolean enabledFor(ListEvent evt) {
return evt.getSelectedRowAccessors().size() == 1 && evt.getSelectedRowAccessors().get(0).getBoolean("GESTION_STOCK");
}
};
getRowActions().add(actionStockShow);
 
}
if (prefs.getBoolean(GestionArticleGlobalPreferencePanel.ACTIVER_DECLINAISON, false)) {
 
RowAction actionConvVirtuel = new RowAction(new AbstractAction("Convertir en article virtuel") {
186,11 → 232,13
 
}
}, true, false) {
 
@Override
public boolean enabledFor(ListEvent evt) {
final List<? extends SQLRowAccessor> selection = evt.getSelectedRowAccessors();
if (selection.size() == 1) {
return !selection.get(0).getBoolean("VIRTUEL") && selection.get(0).isForeignEmpty("ID_ARTICLE_VIRTUEL_PERE");
 
}
return false;
}
218,6 → 266,7
 
}
}, true, false) {
 
@Override
public boolean enabledFor(ListEvent evt) {
final List<? extends SQLRowAccessor> selection = evt.getSelectedRowAccessors();
252,6 → 301,7
 
}
}, false, true) {
 
@Override
public boolean enabledFor(ListEvent evt) {
final List<? extends SQLRowAccessor> selection = evt.getSelectedRowAccessors();
264,6 → 314,7
getRowActions().add(actionCreateDecls);
 
}
 
PredicateRowAction history = new PredicateRowAction(new AbstractAction("Historique") {
 
@Override
287,7 → 338,6
mvtStock.setPredicate(IListeEvent.getSingleSelectionPredicate());
getRowActions().add(mvtStock);
 
if (ComptaPropsConfiguration.getInstanceCompta().isExperimental()) {
PredicateRowAction batches = new PredicateRowAction(new AbstractAction("Lots et numéros de série") {
@Override
public void actionPerformed(ActionEvent e) {
297,7 → 347,7
}, false, true);
batches.setPredicate(IListeEvent.getSingleSelectionPredicate());
getRowActions().add(batches);
}
 
PredicateRowAction clone = new PredicateRowAction(new AbstractAction("Dupliquer") {
 
@Override
398,6 → 448,9
@Override
protected Object show_(SQLRowAccessor r) {
 
if (!r.getBoolean("GESTION_STOCK")) {
return null;
}
BigDecimal totalQte = BigDecimal.ZERO;
 
Collection<? extends SQLRowAccessor> stockElt = r.getReferentRows(getTable().getTable("STOCK").getField("ID_ARTICLE"));
410,9 → 463,10
 
@Override
public Set<FieldPath> getPaths() {
Path p2 = new Path(getTable()).add(getTable().getTable("STOCK").getField("ID_ARTICLE"));
final Path p = new Path(getTable());
Path p2 = p.add(getTable().getTable("STOCK").getField("ID_ARTICLE"));
 
return CollectionUtils.createSet(new FieldPath(p2, "QTE_REEL"));
return CollectionUtils.createSet(new FieldPath(p, "GESTION_STOCK"), new FieldPath(p2, "QTE_REEL"));
}
};
colStockGlobal.setRenderer(new NumberCellRenderer());
441,6 → 495,7
p = p.add(getTable().getTable("ARTICLE_ELEMENT").getField("ID_ARTICLE_PARENT"));
return CollectionUtils.createSet(new FieldPath(p, "QTE"));
}
 
});
}
}
488,10 → 543,10
l.add("POIDS");
l.add("SKU");
 
// if (!prefs.getBoolean(GestionArticleGlobalPreferencePanel.STOCK_MULTI_DEPOT, false)) {
if (!prefs.getBoolean(GestionArticleGlobalPreferencePanel.STOCK_MULTI_DEPOT, false)) {
l.add("GESTION_STOCK");
l.add("ID_STOCK");
// }
}
String val = DefaultNXProps.getInstance().getStringProperty("ArticleService");
Boolean b = Boolean.valueOf(val);
if (b != null && b.booleanValue()) {
995,4 → 1050,19
return mvtStockQuery;
}
 
/**
* Article qui ont comme code les codes fournis en paramètre,
*/
public Map<String, SQLRowAccessor> findArticleFromCode(List<String> codes) {
final SQLRowValues rv = new SQLRowValues(getTable());
rv.setAllToNull();
final SQLRowValuesListFetcher fetcher = SQLRowValuesListFetcher.create(rv);
final List<SQLRowValues> list = fetcher.fetch(Where.inValues(getTable().getField("CODE"), codes));
final Map<String, SQLRowAccessor> result = new HashMap<>(list.size());
for (SQLRowValues r : list) {
result.put(r.getString("CODE"), r);
}
return result;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/LotReceptionSQLElement.java
New file
0,0 → 1,77
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.element;
 
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.sql.element.BaseSQLComponent;
import org.openconcerto.sql.element.SQLComponent;
 
import java.awt.GridBagLayout;
import java.util.ArrayList;
import java.util.List;
 
public class LotReceptionSQLElement extends ComptaSQLConfElement {
 
public LotReceptionSQLElement() {
super("LOT_RECEPTION", "une réception de lot", "réceptions de lots");
}
 
@Override
protected List<String> getListFields() {
final List<String> l = new ArrayList<String>();
l.add("ID_BON_RECEPTION_ELEMENT");
l.add("QUANTITE");
l.add("NUMERO_LOT");
l.add("NUMERO_SERIE");
l.add("DLC");
l.add("DLUO");
return l;
}
 
@Override
protected List<String> getComboFields() {
final List<String> l = new ArrayList<String>();
l.add("ID_BON_RECEPTION_ELEMENT");
l.add("QUANTITE");
l.add("NUMERO_LOT");
l.add("NUMERO_SERIE");
l.add("DLC");
l.add("DLUO");
return l;
}
 
@Override
protected String getParentFFName() {
return "ID_BON_RECEPTION_ELEMENT";
}
 
@Override
public SQLComponent createComponent() {
return new BaseSQLComponent(this) {
 
public void addViews() {
 
this.setLayout(new GridBagLayout());
 
}
};
}
 
@Override
protected String createCode() {
final String string = createCodeOfPackage() + ".batch.receipt";
System.err.println(string);
return string;
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/element/LotLivraisonSQLElement.java
New file
0,0 → 1,77
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.element;
 
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.sql.element.BaseSQLComponent;
import org.openconcerto.sql.element.SQLComponent;
 
import java.awt.GridBagLayout;
import java.util.ArrayList;
import java.util.List;
 
public class LotLivraisonSQLElement extends ComptaSQLConfElement {
 
public LotLivraisonSQLElement() {
super("LOT_LIVRAISON", "une livraison de lot", "livraisons de lots");
}
 
@Override
protected List<String> getListFields() {
final List<String> l = new ArrayList<String>();
l.add("ID_BON_DE_LIVRAISON_ELEMENT");
l.add("QUANTITE");
l.add("NUMERO_LOT");
l.add("NUMERO_SERIE");
l.add("DLC");
l.add("DLUO");
return l;
}
 
@Override
protected List<String> getComboFields() {
final List<String> l = new ArrayList<String>();
l.add("ID_BON__DE_LIVRAISON_ELEMENT");
l.add("QUANTITE");
l.add("NUMERO_LOT");
l.add("NUMERO_SERIE");
l.add("DLC");
l.add("DLUO");
return l;
}
 
@Override
protected String getParentFFName() {
return "ID_BON_DE_LIVRAISON_ELEMENT";
}
 
@Override
public SQLComponent createComponent() {
return new BaseSQLComponent(this) {
 
public void addViews() {
 
this.setLayout(new GridBagLayout());
 
}
};
}
 
@Override
protected String createCode() {
final String string = createCodeOfPackage() + ".batch.delivery";
System.err.println(string);
return string;
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/action/TransfertStockFromArticlePanel.java
New file
0,0 → 1,330
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.action;
 
import org.openconcerto.erp.core.common.ui.NumericTextField;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.erp.core.sales.product.model.ProductComponent;
import org.openconcerto.erp.preferences.GestionArticleGlobalPreferencePanel;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.preferences.SQLPreferences;
import org.openconcerto.sql.request.ComboSQLRequest;
import org.openconcerto.sql.sqlobject.SQLRequestComboBox;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.utils.Tuple2;
import org.openconcerto.utils.text.SimpleDocumentListener;
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.math.BigDecimal;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
 
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
import javax.swing.event.DocumentEvent;
 
import com.lowagie.text.Font;
 
public class TransfertStockFromArticlePanel extends JPanel {
 
private BigDecimal stock = BigDecimal.ZERO;
private final NumericTextField fieldQteTransfert = new NumericTextField(8);
private final JButton buttonUpdate;
private final SQLRequestComboBox comboStockDepart;
private final SQLRequestComboBox comboStockArrive;
final JLabel qteDepotDepart = new JLabel();
final JLabel qteDepotArrive = new JLabel();
final SQLRowAccessor article;
final SQLElement stockDepotElt;
 
public TransfertStockFromArticlePanel(Configuration instance, final SQLRowAccessor article, final SQLRowAccessor depot) {
super(new GridBagLayout());
if (article == null) {
throw new IllegalArgumentException("Article cannot be null");
}
this.article = article;
this.stockDepotElt = instance.getDirectory().getElement("DEPOT_STOCK");
 
this.buttonUpdate = new JButton("Transférer les articles");
this.comboStockDepart = new SQLRequestComboBox();
final JLabel labelStockDepart = new JLabel();
final ComboSQLRequest createComboRequestDepart = this.stockDepotElt.createComboRequest();
final SQLSelect selDepotValid = new SQLSelect();
final SQLTable tableStock = this.stockDepotElt.getTable().getTable("STOCK");
selDepotValid.addSelect(tableStock.getField("ID_DEPOT_STOCK"));
selDepotValid.setWhere(new Where(tableStock.getField("ID_ARTICLE"), "=", article.getID()).and(new Where(tableStock.getField("QTE_REEL"), ">", 0)));
@SuppressWarnings("unchecked")
final List<Number> listDepotValid = tableStock.getDBSystemRoot().getDataSource().executeCol(selDepotValid.asString());
createComboRequestDepart.setWhere(Where.inValues(this.stockDepotElt.getTable().getKey(), listDepotValid));
this.comboStockDepart.uiInit(createComboRequestDepart);
 
this.comboStockArrive = new SQLRequestComboBox();
final ComboSQLRequest createComboRequestArrive = this.stockDepotElt.createComboRequest();
this.comboStockArrive.uiInit(createComboRequestArrive);
 
this.fieldQteTransfert.setText("1");
 
this.qteDepotDepart.setFont(this.qteDepotDepart.getFont().deriveFont(Font.ITALIC));
this.qteDepotArrive.setFont(this.qteDepotDepart.getFont().deriveFont(Font.ITALIC));
this.stock = BigDecimal.ZERO;
this.qteDepotDepart.setText(" ");
this.qteDepotArrive.setText(" ");
this.fieldQteTransfert.getDocument().addDocumentListener(new SimpleDocumentListener() {
 
@Override
public void update(DocumentEvent e) {
updateButtons();
}
});
 
this.comboStockArrive.addModelListener("wantedID", new PropertyChangeListener() {
 
@Override
public void propertyChange(PropertyChangeEvent evt) {
updateButtons();
}
});
 
this.comboStockDepart.addModelListener("wantedID", new PropertyChangeListener() {
 
@Override
public void propertyChange(PropertyChangeEvent evt) {
updateButtons();
}
});
 
GridBagConstraints c = new DefaultGridBagConstraints();
 
if (!article.getString("CODE").trim().isEmpty()) {
c.gridx = 0;
c.gridy++;
c.weightx = 0;
this.add(new JLabel("Code : ", SwingConstants.RIGHT), c);
c.gridx++;
c.weightx = 1;
this.add(new JLabel(article.getString("CODE")), c);
c.gridy++;
}
 
c.gridx = 0;
c.weightx = 0;
this.add(new JLabel("Désignation : ", SwingConstants.RIGHT), c);
c.gridx++;
c.weightx = 1;
this.add(new JLabel(article.getString("NOM")), c);
 
final SQLPreferences prefs = SQLPreferences.getMemCached(article.getTable().getDBRoot());
final boolean hasDeclinaison = prefs.getBoolean(GestionArticleGlobalPreferencePanel.ACTIVER_DECLINAISON, false);
if (hasDeclinaison) {
 
final SQLRowAccessor nonEmptyForeignTaille = article.getNonEmptyForeign("ID_ARTICLE_DECLINAISON_TAILLE");
if (nonEmptyForeignTaille != null) {
c.gridy++;
c.gridx = 0;
c.weightx = 0;
this.add(new JLabel("Taille : ", SwingConstants.RIGHT), c);
c.gridx++;
c.weightx = 1;
this.add(new JLabel(nonEmptyForeignTaille.getString("NOM")), c);
}
 
final SQLRowAccessor nonEmptyForeignCouleur = article.getNonEmptyForeign("ID_ARTICLE_DECLINAISON_COULEUR");
if (nonEmptyForeignCouleur != null) {
c.gridy++;
c.gridx = 0;
c.weightx = 0;
this.add(new JLabel("Couleur : ", SwingConstants.RIGHT), c);
c.gridx++;
c.weightx = 1;
this.add(new JLabel(nonEmptyForeignCouleur.getString("NOM")), c);
}
 
}
 
c.gridy++;
c.gridx = 0;
c.gridwidth = 2;
this.add(new JLabel("Intitulé du transfert"), c);
 
final JTextField label = new JTextField();
c.gridy++;
c.gridx = 0;
 
c.weightx = 1;
this.add(label, c);
label.setText("Transfert de stock");
c.gridwidth = 1;
 
c.gridy++;
c.gridx = 0;
c.weightx = 0;
 
if (depot == null) {
this.add(new JLabel("Du dépôt", SwingConstants.RIGHT), c);
c.gridx++;
this.add(this.comboStockDepart, c);
 
} else {
this.add(new JLabel("Du dépôt : ", SwingConstants.RIGHT), c);
c.gridx++;
this.add(labelStockDepart, c);
labelStockDepart.setText(depot.getString("NOM"));
this.comboStockDepart.setValue(depot);
}
c.gridy++;
c.gridx = 1;
c.weightx = 0;
 
this.add(this.qteDepotDepart, c);
 
c.gridy++;
c.gridx = 0;
c.weightx = 0;
 
this.add(new JLabel("Vers le dépôt", SwingConstants.RIGHT), c);
c.gridx++;
this.add(this.comboStockArrive, c);
 
c.gridy++;
c.gridx = 1;
c.weightx = 0;
this.add(this.qteDepotArrive, c);
 
c.gridy++;
c.gridx = 0;
c.weightx = 0;
this.add(new JLabel("Quantité", SwingConstants.RIGHT), c);
c.gridx++;
c.fill = GridBagConstraints.NONE;
this.add(this.fieldQteTransfert, c);
 
c.gridy++;
c.gridx = 0;
c.weighty = 1;
JButton buttonCancel = new JButton("Annuler");
JPanel pButton = new JPanel();
pButton.add(buttonCancel);
pButton.add(this.buttonUpdate);
c.gridwidth = 2;
c.anchor = GridBagConstraints.SOUTHEAST;
c.weightx = 0;
c.fill = GridBagConstraints.NONE;
this.add(pButton, c);
buttonCancel.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
((JFrame) SwingUtilities.getRoot(TransfertStockFromArticlePanel.this)).dispose();
}
});
this.buttonUpdate.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
TransfertStockFromArticlePanel.this.buttonUpdate.setEnabled(false);
final BigDecimal qteReel = TransfertStockFromArticlePanel.this.fieldQteTransfert.getValue();
instance.getDirectory().getElement(ReferenceArticleSQLElement.class).transfert(Arrays.asList(Tuple2.create(article.asRow(), qteReel)),
TransfertStockFromArticlePanel.this.comboStockDepart.getSelectedRow(), TransfertStockFromArticlePanel.this.comboStockArrive.getSelectedRow(), label.getText(), new Date());
((JFrame) SwingUtilities.getRoot(TransfertStockFromArticlePanel.this)).dispose();
}
});
this.comboStockDepart.addValueListener(new PropertyChangeListener() {
 
@Override
public void propertyChange(PropertyChangeEvent evt) {
if (evt.getNewValue() != null) {
int fromId = (Integer) evt.getNewValue();
List<SQLRowValues> list = createComboRequestArrive.getValues();
for (SQLRowValues row : list) {
if (row.getID() != fromId) {
TransfertStockFromArticlePanel.this.comboStockArrive.setValue(row.getID());
break;
}
}
}
}
});
if (depot == null) {
if (!listDepotValid.isEmpty()) {
this.comboStockDepart.setValue(listDepotValid.get(0).intValue());
} else {
// Aucun stock
SwingUtilities.invokeLater(new Runnable() {
 
@Override
public void run() {
JOptionPane.showMessageDialog(TransfertStockFromArticlePanel.this, "Aucun stock pour cet article");
((JFrame) SwingUtilities.getRoot(TransfertStockFromArticlePanel.this)).dispose();
 
}
});
}
}
SwingUtilities.invokeLater(new Runnable() {
 
@Override
public void run() {
TransfertStockFromArticlePanel.this.fieldQteTransfert.grabFocus();
updateButtons();
}
});
 
}
 
private void updateButtons() {
final BigDecimal qte = this.fieldQteTransfert.getValue();
this.buttonUpdate.setEnabled(this.stock.signum() > 0 && qte.signum() > 0 && this.stock.subtract(qte).signum() >= 0 && this.comboStockArrive.getSelectedRow() != null
&& this.comboStockDepart.getSelectedRow() != null && this.comboStockArrive.getSelectedRow().getID() != this.comboStockDepart.getSelectedRow().getID());
 
final int idDepart = TransfertStockFromArticlePanel.this.comboStockDepart.getWantedID();
if (idDepart != SQLRow.NONEXISTANT_ID) {
SQLRowAccessor stockRow = ProductComponent.findOrCreateStock(this.article, this.stockDepotElt.getTable().getRow(idDepart));
TransfertStockFromArticlePanel.this.stock = new BigDecimal(stockRow.getFloat("QTE_REEL"));
this.qteDepotDepart.setText(String.valueOf(TransfertStockFromArticlePanel.this.stock) + " en stock -> " + String.valueOf(TransfertStockFromArticlePanel.this.stock.subtract(qte)));
} else {
TransfertStockFromArticlePanel.this.stock = BigDecimal.ZERO;
this.qteDepotDepart.setText("pas de dépôt sélectionné");
}
 
final int idArrive = TransfertStockFromArticlePanel.this.comboStockArrive.getWantedID();
if (idArrive != SQLRow.NONEXISTANT_ID) {
SQLRowAccessor stockRow = ProductComponent.findOrCreateStock(this.article, this.stockDepotElt.getTable().getRow(idArrive));
BigDecimal stockArrive = new BigDecimal(stockRow.getFloat("QTE_REEL"));
this.qteDepotArrive.setText(String.valueOf(stockArrive) + " en stock -> " + String.valueOf(stockArrive.add(qte)));
} else {
this.qteDepotArrive.setText("pas de dépôt sélectionné");
}
 
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/action/TransfertStockPanel.java
17,6 → 17,8
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.request.ComboSQLRequest;
import org.openconcerto.sql.sqlobject.SQLRequestComboBox;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.JDate;
53,8 → 55,11
final ReferenceArticleSQLElement articleElt = instance.getDirectory().getElement(ReferenceArticleSQLElement.class);
 
final SQLRequestComboBox comboArticle = new SQLRequestComboBox();
comboArticle.uiInit(articleElt.createComboRequest());
 
final ComboSQLRequest createComboRequest = articleElt.createComboRequest();
createComboRequest.putWhere("obsolete", new Where(articleElt.getTable().getField("OBSOLETE"), "=", Boolean.FALSE));
comboArticle.uiInit(createComboRequest);
 
final SQLElement stockElt = instance.getDirectory().getElement("DEPOT_STOCK");
final SQLRequestComboBox comboStockDepart = new SQLRequestComboBox();
comboStockDepart.uiInit(stockElt.createComboRequest());
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/ui/DeliveredQtyRowValuesRenderer.java
File deleted
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/ui/DeliveryNoteQtyRowValuesRenderer.java
New file
0,0 → 1,91
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.ui;
 
import org.openconcerto.erp.core.sales.product.component.BatchSelectorFrame;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.view.list.RowValuesTable;
import org.openconcerto.sql.view.list.RowValuesTableModel;
 
import java.awt.BorderLayout;
import java.awt.Component;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
 
import javax.swing.ImageIcon;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTable;
 
/**
* Renderer de quantité pour les bons de livraison
*/
public class DeliveryNoteQtyRowValuesRenderer extends QtyRowValuesRenderer {
private final ImageIcon iOk;
private final ImageIcon iError;
 
public DeliveryNoteQtyRowValuesRenderer() {
super(true);
this.iOk = new ImageIcon(BatchSelectorFrame.class.getResource("batch.png"));
this.iError = new ImageIcon(BatchSelectorFrame.class.getResource("batch_error.png"));
}
 
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
 
final Component comp = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
 
if (table instanceof RowValuesTable) {
 
final RowValuesTable rowValuesTable = (RowValuesTable) table;
final JLabel text = ((JLabel) comp);
 
final RowValuesTableModel model = rowValuesTable.getRowValuesTableModel();
 
final SQLRowValues rowValsBonLivraisonItem = model.getRowValuesAt(row);
 
final List<String> batchField = Arrays.asList("DLC_REQUIS", "DLUO_REQUIS", "NUMERO_LOT_REQUIS", "NUMERO_SERIE_REQUIS");
boolean productRequireBatch = false;
final SQLRowAccessor foreign = rowValsBonLivraisonItem.getNonEmptyForeign("ID_ARTICLE");
if (foreign != null) {
for (String field : batchField) {
if (foreign.getBoolean(field)) {
productRequireBatch = true;
break;
}
}
}
if (productRequireBatch) {
final Collection<SQLRowValues> referentRows = rowValsBonLivraisonItem.getReferentRows(rowValsBonLivraisonItem.getTable().getTable("LOT_LIVRAISON"));
final boolean batchMissing = referentRows.isEmpty();
final JLabel label = new JLabel(" ");
if (batchMissing) {
label.setIcon(this.iError);
} else {
label.setIcon(this.iOk);
}
final JPanel p = new JPanel();
p.setLayout(new BorderLayout());
p.add(text, BorderLayout.CENTER);
p.add(label, BorderLayout.WEST);
p.setBackground(text.getBackground());
label.setOpaque(false);
return p;
}
}
return comp;
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/ui/QtyRowValuesRenderer.java
New file
0,0 → 1,93
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.ui;
 
import org.openconcerto.erp.core.common.ui.DeviseNiceTableCellRenderer;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.view.list.RowValuesTable;
import org.openconcerto.sql.view.list.RowValuesTableModel;
import org.openconcerto.ui.table.AlternateTableCellRenderer;
import org.openconcerto.ui.table.XTableColumnModel;
import org.openconcerto.utils.CollectionUtils;
 
import java.awt.Color;
import java.awt.Component;
 
import javax.swing.JLabel;
import javax.swing.JTable;
import javax.swing.SwingConstants;
 
public class QtyRowValuesRenderer extends DeviseNiceTableCellRenderer {
 
// Red
public static final Color red = new Color(255, 31, 52);
public static final Color redLightGrey = new Color(240, 65, 85);
 
// Orange
public final static Color orange = new Color(243, 125, 75);
public final static Color orangeGrey = new Color(222, 107, 47);
 
// Blue
public final static Color light = new Color(232, 238, 250);
public final static Color lightGrey = new Color(211, 220, 222);
 
// Black
public final static Color lightBlack = new Color(192, 192, 192);
public final static Color lightBlackGrey = new Color(155, 155, 155);
 
private final boolean customer;
 
public QtyRowValuesRenderer(boolean customer) {
AlternateTableCellRenderer.setBGColorMap(this, CollectionUtils.createMap(lightBlack, lightBlackGrey, red, redLightGrey, orange, orangeGrey));
this.customer = customer;
}
 
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
 
Component comp = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
 
if (table instanceof RowValuesTable) {
 
((JLabel) comp).setHorizontalAlignment(SwingConstants.RIGHT);
RowValuesTable rowValuesTable = (RowValuesTable) table;
XTableColumnModel columnModel = rowValuesTable.getColumnModel();
RowValuesTableModel model = rowValuesTable.getRowValuesTableModel();
boolean qteALivrerVisible = columnModel.isColumnVisible(columnModel.getColumnByModelIndex(model.getColumnForField("QTE_A_LIVRER")));
if (qteALivrerVisible) {
SQLRowValues rowVals = model.getRowValuesAt(row);
 
Number qte;
Number qteL;
if (this.customer) {
qte = (Number) rowVals.getObject("QTE");
qteL = (Number) rowVals.getObject("QTE_LIVREE");
} else {
qte = (Number) rowVals.getObject("QTE_ORIGINE");
qteL = (Number) rowVals.getObject("QTE");
}
if (qte != null && qteL != null) {
if (qte.intValue() < qteL.intValue()) {
comp.setBackground(red);
} else if (qteL.intValue() <= 0) {
comp.setBackground(lightBlack);
} else if (qteL.intValue() != qte.intValue()) {
comp.setBackground(orange);
}
}
}
}
return comp;
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/ui/ListeDesArticlesFrame.java
15,6 → 15,7
 
import org.openconcerto.erp.config.Log;
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.common.ui.IListTotalPanel;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.erp.panel.ITreeSelection;
import org.openconcerto.erp.preferences.GestionArticleGlobalPreferencePanel;
42,6 → 43,7
import org.openconcerto.ui.PanelFrame;
import org.openconcerto.utils.CollectionUtils;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.Tuple2;
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
212,6 → 214,20
panelMode.setBorder(BorderFactory.createTitledBorder("Vue"));
panel.add(panelMode, c2);
}
 
SQLTableModelColumn colStock = null;
for (SQLTableModelColumn col : panel.getListe().getSource().getColumns()) {
if (col.getName().equalsIgnoreCase("Valeur HT du stock")) {
colStock = col;
}
}
if (colStock != null) {
List<Tuple2<? extends SQLTableModelColumn, IListTotalPanel.Type>> fields = new ArrayList<Tuple2<? extends SQLTableModelColumn, IListTotalPanel.Type>>(1);
fields.add(Tuple2.create(colStock, IListTotalPanel.Type.SOMME));
IListTotalPanel total = new IListTotalPanel(panel.getListe(), fields, null, "Total");
c2.gridy++;
panel.add(total, c2);
}
JSplitPane pane = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT, new JScrollPane(panelFam), panel);
JPanel panelAll = new JPanel(new GridBagLayout());
GridBagConstraints c = new DefaultGridBagConstraints();
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/model/BatchQuantity.java
New file
0,0 → 1,53
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.model;
 
import java.math.BigDecimal;
 
public class BatchQuantity {
private final int idBatch;
private BigDecimal quantity;
private BigDecimal quantityInDB;
 
public BatchQuantity(int idBatch, BigDecimal quantity, BigDecimal quantityInDB) {
this.idBatch = idBatch;
this.quantity = quantity;
this.quantityInDB = quantityInDB;
}
 
public BigDecimal getQuantityInDB() {
return quantityInDB;
}
 
public void setQuantityInDB(BigDecimal quantityInDB) {
this.quantityInDB = quantityInDB;
}
 
public BigDecimal getQuantity() {
return this.quantity;
}
 
public int getIdBatch() {
return this.idBatch;
}
 
public void addQuantity(BigDecimal bigDecimal) {
this.quantity = this.quantity.add(bigDecimal);
}
 
public void setQuantity(BigDecimal newQty) {
this.quantity = newQty;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/component/BatchSelectorFrame.java
New file
0,0 → 1,654
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.product.component;
 
import org.openconcerto.erp.core.sales.product.element.LotSQLElement;
import org.openconcerto.erp.core.sales.product.model.BatchQuantity;
import org.openconcerto.erp.core.supplychain.receipt.ui.BatchQuantityRenderer;
import org.openconcerto.erp.core.supplychain.receipt.ui.BatchQuantityTableCellEditor;
import org.openconcerto.erp.core.supplychain.stock.element.StockSQLElement;
import org.openconcerto.sql.element.SQLElementDirectory;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLSelectJoin;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.Where;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.JLabelBold;
import org.openconcerto.ui.VerticalLayout;
import org.openconcerto.ui.table.AlternateTableCellRenderer;
import org.openconcerto.utils.cc.ITransformer;
 
import java.awt.FlowLayout;
import java.awt.Frame;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
 
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.SwingWorker;
import javax.swing.event.TableModelEvent;
import javax.swing.event.TableModelListener;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumn;
 
public class BatchSelectorFrame extends JDialog {
 
private SQLElementDirectory dir;
private SQLRow product;
// Quantités sélectionnées
private List<BatchQuantity> quantities = new ArrayList<>();
// Tous les lots de l'article actuel
private List<SQLRowValues> all = new ArrayList<>();
private Map<Integer, SQLRowValues> mapAll = new HashMap<>();
// Tous les lots de l'article avec qté > 0
private List<SQLRowValues> available = new ArrayList<>();
private JTable leftTable;
private JTable rightTable;
private JLabel productName = new JLabel("...");
private JButton toRigthButton;
private JButton toLeftButton;
 
private DefaultTableModel leftModel;
 
private DefaultTableModel rightModel;
 
//
private final int C_STOCK = 0;
private final int C_QUANTITY = 1;
private final int C_BATCH = 2;
private final int C_DLC = 3;
private final int C_DLUO = 4;
private final int C_SERIAL = 5;
 
private boolean cancelled = false;
 
public BatchSelectorFrame(Frame owner, SQLElementDirectory dir, SQLRow product, List<BatchQuantity> list) {
super(owner);
this.dir = dir;
this.product = product;
for (BatchQuantity q : list) {
this.quantities.add(new BatchQuantity(q.getIdBatch(), q.getQuantity(), q.getQuantityInDB()));
}
this.addWindowListener(new WindowAdapter() {
@Override
public void windowOpened(WindowEvent e) {
loadData();
}
});
//
this.setLayout(new GridBagLayout());
final GridBagConstraints c = new DefaultGridBagConstraints();
c.weightx = 1;
c.gridwidth = 3;
c.weighty = 0;
this.productName.setText(product.getString("NOM"));
this.add(this.productName, c);
// Titres
c.gridy++;
c.gridwidth = 1;
c.gridx = 0;
c.weightx = 1;
this.add(new JLabelBold("En stock"), c);
c.gridx = 2;
this.add(new JLabelBold("Sélection"), c);
// Tables
c.weighty = 1;
c.fill = GridBagConstraints.BOTH;
c.gridy++;
c.gridx = 0;
c.weightx = 1;
this.leftModel = createLeftTableModel();
this.leftTable = new JTable(this.leftModel);
this.add(new JScrollPane(this.leftTable), c);
this.leftTable.getModel().addTableModelListener(new TableModelListener() {
 
@Override
public void tableChanged(TableModelEvent e) {
if (e.getType() == TableModelEvent.HEADER_ROW) {
if (leftTable.getColumnCount() > 2) {
final BatchQuantityTableCellEditor qtyEditor = new BatchQuantityTableCellEditor(product.getForeignIDNumber("ID_UNITE_VENTE"));
final TableColumn qtyCol = leftTable.getColumnModel().getColumn(1);
qtyCol.setCellEditor(qtyEditor);
qtyCol.setCellRenderer(new BatchQuantityRenderer());
}
}
}
});
 
c.gridx++;
c.weightx = 0;
final JPanel moveButtons = new JPanel();
moveButtons.setOpaque(false);
moveButtons.setLayout(new VerticalLayout());
this.toRigthButton = new JButton(">");
moveButtons.add(this.toRigthButton);
this.toLeftButton = new JButton("<");
moveButtons.add(this.toLeftButton);
this.add(moveButtons, c);
c.gridx++;
c.weightx = 1;
this.rightModel = createRightTableModel();
this.rightTable = new JTable(this.rightModel);
this.add(new JScrollPane(this.rightTable), c);
// this.rightTable.getModel().addTableModelListener(new TableModelListener() {
//
// @Override
// public void tableChanged(TableModelEvent e) {
// if (e.getType() == TableModelEvent.HEADER_ROW) {
// if (rightTable.getColumnCount() > 1) {
// final BatchQuantityTableCellEditor qtyEditor = new
// BatchQuantityTableCellEditor(product.getForeignIDNumber("ID_UNITE_VENTE"));
// final TableColumn qtyCol = rightTable.getColumnModel().getColumn(1);
// qtyCol.setCellEditor(qtyEditor);
// qtyCol.setCellRenderer(new BatchQuantityRenderer());
//
// }
// }
// }
// });
//
final JPanel buttons = new JPanel();
buttons.setLayout(new FlowLayout());
buttons.setOpaque(false);
final JButton cancelButton = new JButton("Annuler");
 
final JButton closeButton = new JButton("Fermer");
 
buttons.add(cancelButton);
buttons.add(closeButton);
c.gridy++;
c.gridwidth++;
c.fill = GridBagConstraints.NONE;
c.anchor = GridBagConstraints.EAST;
this.add(buttons, c);
 
// Listeners
this.toRigthButton.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
final int[] rows = BatchSelectorFrame.this.leftTable.getSelectedRows();
if (rows.length > 0) {
final List<SQLRowValues> toRemove = new ArrayList<>();
for (int i = 0; i < rows.length; i++) {
final int rowIndex = rows[i];
final SQLRowValues rv = BatchSelectorFrame.this.available.get(rowIndex);
final int idBatch = rv.getID();
BatchQuantity found = null;
for (BatchQuantity q : BatchSelectorFrame.this.quantities) {
if (q.getIdBatch() == idBatch) {
found = q;
break;
}
}
if (found == null) {
found = new BatchQuantity(idBatch, BigDecimal.ZERO, BigDecimal.ZERO);
BatchSelectorFrame.this.quantities.add(found);
}
found.addQuantity(rv.getBigDecimal("QUANTITE"));
rv.put("QUANTITE", BigDecimal.ZERO);
toRemove.add(rv);
}
BatchSelectorFrame.this.available.removeAll(toRemove);
dataChanged();
}
 
}
});
this.toLeftButton.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
final int[] rows = BatchSelectorFrame.this.rightTable.getSelectedRows();
if (rows.length > 0) {
final List<BatchQuantity> toRemove = new ArrayList<>();
for (int i = 0; i < rows.length; i++) {
final int rowIndex = rows[i];
final BatchQuantity q = BatchSelectorFrame.this.quantities.get(rowIndex);
SQLRowValues found = null;
for (SQLRowValues rv : BatchSelectorFrame.this.available) {
if (q.getIdBatch() == rv.getID()) {
found = rv;
break;
}
}
if (found == null) {
found = BatchSelectorFrame.this.mapAll.get(q.getIdBatch());
BatchSelectorFrame.this.available.add(found);
}
found.put("QUANTITE", found.getBigDecimal("QUANTITE").add(q.getQuantity()));
toRemove.add(q);
}
BatchSelectorFrame.this.quantities.removeAll(toRemove);
dataChanged();
}
 
}
});
cancelButton.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
cancelled = true;
dispose();
}
});
closeButton.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
dispose();
}
});
 
}
 
public boolean isCancelled() {
return cancelled;
}
 
public BigDecimal getTotalSelectedQuantity() {
BigDecimal total = BigDecimal.ZERO;
for (int i = 0; i < this.rightTable.getRowCount(); i++) {
total = total.add((BigDecimal) this.rightTable.getValueAt(i, 0));
}
return total;
}
 
private DefaultTableModel createLeftTableModel() {
DefaultTableModel model = new DefaultTableModel() {
 
private final List<Integer> cols = new ArrayList<>();
 
@Override
public Object getValueAt(int row, int column) {
SQLRowValues r = BatchSelectorFrame.this.available.get(row);
int c = this.cols.get(column);
if (c == BatchSelectorFrame.this.C_STOCK) {
return r.getForeign("ID_STOCK").getForeign("ID_DEPOT_STOCK").getString("NOM");
} else if (c == BatchSelectorFrame.this.C_QUANTITY) {
return r.getBigDecimal("QUANTITE");
} else if (c == BatchSelectorFrame.this.C_BATCH) {
return r.getString("NUMERO_LOT");
} else if (c == BatchSelectorFrame.this.C_DLC) {
return r.getDate("DLC").getTime();
} else if (c == BatchSelectorFrame.this.C_DLUO) {
return r.getDate("DLUO").getTime();
} else if (c == BatchSelectorFrame.this.C_SERIAL) {
return r.getString("NUMERO_SERIE");
} else {
return "??" + c;
}
}
 
@Override
public boolean isCellEditable(int row, int column) {
return false;
}
 
@Override
public int getColumnCount() {
if (this.cols == null) {
// null when called from the DefaultTableModel constructor
return 0;
}
return this.cols.size();
}
 
@Override
public int getRowCount() {
return BatchSelectorFrame.this.available.size();
}
 
@Override
public String getColumnName(int column) {
int c = this.cols.get(column);
if (c == BatchSelectorFrame.this.C_STOCK) {
return "Stock";
} else if (c == BatchSelectorFrame.this.C_QUANTITY) {
return "Quantité";
} else if (c == BatchSelectorFrame.this.C_BATCH) {
return "Lot";
} else if (c == BatchSelectorFrame.this.C_DLC) {
return "D.L.C.";
} else if (c == BatchSelectorFrame.this.C_DLUO) {
return "D.L.U.O.";
} else if (c == BatchSelectorFrame.this.C_SERIAL) {
return "N° de série";
} else {
return "??" + c;
}
}
 
@Override
public Class<?> getColumnClass(int columnIndex) {
int c = this.cols.get(columnIndex);
if (c == BatchSelectorFrame.this.C_STOCK) {
return String.class;
} else if (c == BatchSelectorFrame.this.C_QUANTITY) {
return BigDecimal.class;
} else if (c == BatchSelectorFrame.this.C_BATCH) {
return String.class;
} else if (c == BatchSelectorFrame.this.C_DLC) {
return Date.class;
} else if (c == BatchSelectorFrame.this.C_DLUO) {
return Date.class;
} else if (c == BatchSelectorFrame.this.C_SERIAL) {
return String.class;
} else {
return String.class;
}
}
 
@Override
public void fireTableDataChanged() {
this.cols.clear();
this.cols.add(BatchSelectorFrame.this.C_STOCK);
this.cols.add(BatchSelectorFrame.this.C_QUANTITY);
for (SQLRowValues r : BatchSelectorFrame.this.available) {
if (!r.getString("NUMERO_LOT").isEmpty()) {
this.cols.add(BatchSelectorFrame.this.C_BATCH);
break;
}
}
for (SQLRowValues r : BatchSelectorFrame.this.available) {
if (r.getObject("DCL") != null) {
this.cols.add(BatchSelectorFrame.this.C_DLC);
break;
}
}
for (SQLRowValues r : BatchSelectorFrame.this.available) {
if (r.getObject("DLUO") != null) {
this.cols.add(BatchSelectorFrame.this.C_DLUO);
break;
}
}
for (SQLRowValues r : BatchSelectorFrame.this.available) {
if (!r.getString("NUMERO_SERIE").isEmpty()) {
this.cols.add(BatchSelectorFrame.this.C_SERIAL);
break;
}
}
 
super.fireTableDataChanged();
}
 
@Override
public void fireTableStructureChanged() {
super.fireTableStructureChanged();
if (leftTable != null && leftTable.getColumnCount() > 1) {
final BatchQuantityTableCellEditor qtyEditor = new BatchQuantityTableCellEditor(product.getForeignIDNumber("ID_UNITE_VENTE"));
final TableColumn qtyCol = leftTable.getColumnModel().getColumn(1);
qtyCol.setCellEditor(qtyEditor);
qtyCol.setCellRenderer(new BatchQuantityRenderer());
AlternateTableCellRenderer.UTILS.setAllColumns(leftTable);
}
}
 
};
 
return model;
}
 
private DefaultTableModel createRightTableModel() {
DefaultTableModel model = new DefaultTableModel() {
 
private final List<Integer> cols = new ArrayList<>();
 
@Override
public Object getValueAt(int row, int column) {
BatchQuantity b = BatchSelectorFrame.this.quantities.get(row);
int c = this.cols.get(column);
if (c == BatchSelectorFrame.this.C_QUANTITY) {
return b.getQuantity();
} else if (c == BatchSelectorFrame.this.C_BATCH) {
SQLRowValues r = BatchSelectorFrame.this.mapAll.get(b.getIdBatch());
return r.getString("NUMERO_LOT");
} else if (c == BatchSelectorFrame.this.C_DLC) {
SQLRowValues r = BatchSelectorFrame.this.mapAll.get(b.getIdBatch());
return r.getDate("DLC").getTime();
} else if (c == BatchSelectorFrame.this.C_DLUO) {
SQLRowValues r = BatchSelectorFrame.this.mapAll.get(b.getIdBatch());
return r.getDate("DLUO").getTime();
} else if (c == BatchSelectorFrame.this.C_SERIAL) {
SQLRowValues r = BatchSelectorFrame.this.mapAll.get(b.getIdBatch());
return r.getString("NUMERO_SERIE");
} else {
return "??" + c;
}
}
 
@Override
public boolean isCellEditable(int row, int column) {
return column == 0;
}
 
@Override
public void setValueAt(Object aValue, int row, int column) {
if (column == 0) {
BigDecimal newQty = (BigDecimal) aValue;
BigDecimal previousQty = (BigDecimal) getValueAt(row, column);
if (newQty.compareTo(BigDecimal.ZERO) > 0 && newQty.compareTo(previousQty) < 0) {
BatchSelectorFrame.this.quantities.get(row).setQuantity(newQty);
final SQLRowValues rv = BatchSelectorFrame.this.mapAll.get(BatchSelectorFrame.this.quantities.get(row).getIdBatch());
if (!BatchSelectorFrame.this.available.contains(rv)) {
BatchSelectorFrame.this.available.add(rv);
}
rv.put("QUANTITE", rv.getBigDecimal("QUANTITE").add(previousQty).subtract(newQty));
BatchSelectorFrame.this.leftModel.fireTableDataChanged();
BatchSelectorFrame.this.leftModel.fireTableStructureChanged();
 
}
 
}
}
 
@Override
public int getColumnCount() {
if (this.cols == null) {
// null when called from the DefaultTableModel constructor
return 0;
}
return this.cols.size();
 
}
 
@Override
public int getRowCount() {
return BatchSelectorFrame.this.quantities.size();
}
 
@Override
public String getColumnName(int column) {
int c = this.cols.get(column);
if (c == BatchSelectorFrame.this.C_QUANTITY) {
return "Quantité";
} else if (c == BatchSelectorFrame.this.C_BATCH) {
return "Lot";
} else if (c == BatchSelectorFrame.this.C_DLC) {
return "D.L.C.";
} else if (c == BatchSelectorFrame.this.C_DLUO) {
return "D.L.U.O.";
} else if (c == BatchSelectorFrame.this.C_SERIAL) {
return "N° de série";
} else {
return "??" + c;
}
}
 
@Override
public Class<?> getColumnClass(int columnIndex) {
int c = this.cols.get(columnIndex);
if (c == BatchSelectorFrame.this.C_STOCK) {
return String.class;
} else if (c == BatchSelectorFrame.this.C_QUANTITY) {
return BigDecimal.class;
} else if (c == BatchSelectorFrame.this.C_BATCH) {
return String.class;
} else if (c == BatchSelectorFrame.this.C_DLC) {
return Date.class;
} else if (c == BatchSelectorFrame.this.C_DLUO) {
return Date.class;
} else if (c == BatchSelectorFrame.this.C_SERIAL) {
return String.class;
} else {
return String.class;
}
}
 
@Override
public void fireTableDataChanged() {
this.cols.clear();
this.cols.add(BatchSelectorFrame.this.C_QUANTITY);
List<SQLRowValues> values = new ArrayList<>();
for (BatchQuantity q : BatchSelectorFrame.this.quantities) {
values.add(BatchSelectorFrame.this.mapAll.get(q.getIdBatch()));
}
 
for (SQLRowValues r : values) {
if (!r.getString("NUMERO_LOT").isEmpty()) {
this.cols.add(BatchSelectorFrame.this.C_BATCH);
break;
}
}
for (SQLRowValues r : values) {
if (r.getObject("DCL") != null) {
this.cols.add(BatchSelectorFrame.this.C_DLC);
break;
}
}
for (SQLRowValues r : values) {
if (r.getObject("DLUO") != null) {
this.cols.add(BatchSelectorFrame.this.C_DLUO);
break;
}
}
for (SQLRowValues r : values) {
if (!r.getString("NUMERO_SERIE").isEmpty()) {
this.cols.add(BatchSelectorFrame.this.C_SERIAL);
break;
}
}
super.fireTableDataChanged();
 
}
 
@Override
public void fireTableStructureChanged() {
super.fireTableStructureChanged();
if (rightTable != null && rightTable.getColumnCount() > 0) {
final BatchQuantityTableCellEditor qtyEditor = new BatchQuantityTableCellEditor(product.getForeignIDNumber("ID_UNITE_VENTE"));
final TableColumn qtyCol = rightTable.getColumnModel().getColumn(0);
qtyCol.setCellEditor(qtyEditor);
qtyCol.setCellRenderer(new BatchQuantityRenderer());
AlternateTableCellRenderer.UTILS.setAllColumns(rightTable);
}
}
 
};
 
return model;
}
 
protected void loadData() {
final List<Integer> ids = new ArrayList<>();
for (BatchQuantity batchQuantity : this.quantities) {
ids.add(batchQuantity.getIdBatch());
}
 
SwingWorker<List<SQLRowValues>, List<SQLRowValues>> worker = new SwingWorker<List<SQLRowValues>, List<SQLRowValues>>() {
 
@Override
protected List<SQLRowValues> doInBackground() throws Exception {
final SQLTable batchTable = BatchSelectorFrame.this.dir.getElement(LotSQLElement.class).getTable();
final SQLTable stockTable = BatchSelectorFrame.this.dir.getElement(StockSQLElement.class).getTable();
final SQLRowValues r = new SQLRowValues(batchTable);
r.putNulls(batchTable.getFieldsName());
final SQLRowValues rStock = r.putRowValues("ID_STOCK");
rStock.putNulls(stockTable.getFieldsName());
rStock.putRowValues("ID_DEPOT_STOCK").putNulls("NOM");
 
final SQLRowValuesListFetcher fetcher = SQLRowValuesListFetcher.create(r);
fetcher.setSelTransf(new ITransformer<SQLSelect, SQLSelect>() {
 
@Override
public SQLSelect transformChecked(SQLSelect input) {
final SQLSelectJoin join = input.getJoin(batchTable.getField("ID_STOCK"));
final Where w = Where.inValues(batchTable.getKey(), ids);
final Where wSameProduct = new Where(join.getJoinedTable().getField("ID_ARTICLE"), "=", BatchSelectorFrame.this.product.getID());
final Where wNotEmpty = new Where(batchTable.getField("QUANTITE"), ">", 0);
input.setWhere((w.or(wNotEmpty).and(wSameProduct)));
System.err.println(input.asString());
return input;
}
});
return fetcher.fetch();
 
}
 
protected void done() {
try {
List<SQLRowValues> r = get();
BatchSelectorFrame.this.all.clear();
BatchSelectorFrame.this.all.addAll(r);
BatchSelectorFrame.this.mapAll.clear();
BatchSelectorFrame.this.available.clear();
for (SQLRowValues v : BatchSelectorFrame.this.all) {
if (v.getBigDecimal("QUANTITE").compareTo(BigDecimal.ZERO) > 0) {
BatchSelectorFrame.this.available.add(v);
}
BatchSelectorFrame.this.mapAll.put(v.getID(), v);
}
dataChanged();
;
} catch (Exception e) {
e.printStackTrace();
}
};
 
};
worker.execute();
 
}
 
public List<BatchQuantity> getQuantities() {
return this.quantities;
}
 
public void dataChanged() {
 
BatchSelectorFrame.this.leftModel.fireTableDataChanged();
BatchSelectorFrame.this.leftModel.fireTableStructureChanged();
BatchSelectorFrame.this.rightModel.fireTableDataChanged();
BatchSelectorFrame.this.rightModel.fireTableStructureChanged();
 
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/component/batch_error.png
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/component/batch_error.png
New file
Property changes:
Added: svn:mime-type
+application/octet-stream
\ No newline at end of property
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/component/batch.png
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/component/batch.png
New file
Property changes:
Added: svn:mime-type
+application/octet-stream
\ No newline at end of property
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/product/component/ReferenceArticleSQLComponent.java
925,18 → 925,22
c.gridx = 1;
c.weightx = 1;
JCheckBox DLCrequis = new JCheckBox("DLC requis");
DLCrequis.setOpaque(false);
panel.add(DLCrequis, c);
addView(DLCrequis, "DLC_REQUIS");
c.gridy++;
JCheckBox DLUOrequis = new JCheckBox("DLUO requis");
DLUOrequis.setOpaque(false);
panel.add(DLUOrequis, c);
addView(DLUOrequis, "DLUO_REQUIS");
c.gridy++;
JCheckBox numeroLotRequis = new JCheckBox("n° de lot requis");
numeroLotRequis.setOpaque(false);
panel.add(numeroLotRequis, c);
addView(numeroLotRequis, "NUMERO_LOT_REQUIS");
c.gridy++;
JCheckBox numeroSerieRequis = new JCheckBox("n° de série requis");
numeroSerieRequis.setOpaque(false);
panel.add(numeroSerieRequis, c);
addView(numeroSerieRequis, "NUMERO_SERIE_REQUIS");
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/BarcodeListener.java
File deleted
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/PaiementPanel.java
13,6 → 13,8
package org.openconcerto.erp.core.sales.pos.ui;
 
import org.openconcerto.erp.core.sales.pos.io.Barcode;
import org.openconcerto.erp.core.sales.pos.io.BarcodeListener;
import org.openconcerto.erp.core.sales.pos.model.Article;
import org.openconcerto.erp.core.sales.pos.model.Paiement;
import org.openconcerto.erp.core.sales.pos.model.TicketItem;
547,7 → 549,7
}
 
@Override
public void barcodeRead(String code) {
public void barcodeRead(Barcode code) {
// Nothing to do here
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/ArticleSelector.java
18,6 → 18,7
import org.openconcerto.ui.touch.ScrollableList;
import org.openconcerto.utils.QuickOrderedMap;
import org.openconcerto.utils.StringUtils;
import org.openconcerto.utils.Tuple2;
 
import java.awt.Color;
import java.awt.FlowLayout;
214,13 → 215,14
label += " [" + article.getCode() + "]";
}
StringBuilder declinaisons = null;
QuickOrderedMap<String, String> decls = article.getDeclinaisons();
QuickOrderedMap<String, Tuple2<String, BigDecimal>> decls = article.getDeclinaisons();
if (decls != null && !decls.isEmpty()) {
declinaisons = new StringBuilder();
for (int i = 0; i < decls.size(); i++) {
declinaisons.append(StringUtils.firstUpThenLow(decls.getKey(i)));
declinaisons.append(": ");
declinaisons.append(decls.getValue(i));
final Tuple2<String, BigDecimal> value = decls.getValue(i);
declinaisons.append(value.get0());
declinaisons.append(" ");
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/CaissePanel.java
36,6 → 36,7
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.FileUtils;
import org.openconcerto.utils.StringUtils;
import org.openconcerto.utils.Tuple2;
import org.openconcerto.utils.cc.ITransformer;
 
import java.awt.Color;
222,7 → 223,8
Map<TicketItem, Integer> missingQty = new HashMap<>();
for (SQLRow row : SQLRowListRSH.execute(selStock)) {
int idArticle = row.getInt("ID_ARTICLE");
int qte = (int) Math.round(row.getFloat("QTE_REEL"));
// Limite pour ne pas fixer les stock négatif et corrompre le stock principal
int qte = Math.max(0, (int) Math.round(row.getFloat("QTE_REEL")));
TicketItem item = mapTicketItem.get(idArticle);
if (item == null) {
System.err.println("Pas d'entrée dans STOCK pour l'article " + idArticle);
318,8 → 320,8
final SQLSelect selArticle = new SQLSelect();
final SQLTable tableArticle = eltArticle.getTable();
selArticle.addAllSelect(tableArticle.getFields(VirtualFields.PRIMARY_KEY.union(VirtualFields.ARCHIVE)));
selArticle.addAllSelect(tableArticle,
Arrays.asList("ID_FAMILLE_ARTICLE", "NOM", "CODE", "CODE_BARRE", "ID_TAXE", "PV_HT", "PV_TTC", "ADDITIONAL_TICKET_COPY", "ID_UNITE_VENTE", "ID_ECO_CONTRIBUTION"));
selArticle.addAllSelect(tableArticle, Arrays.asList("ID_ARTICLE_VIRTUEL_PERE", "ID_FAMILLE_ARTICLE", "NOM", "CODE", "CODE_BARRE", "ID_TAXE", "PV_HT", "PV_TTC", "ADDITIONAL_TICKET_COPY",
"ID_UNITE_VENTE", "ID_ECO_CONTRIBUTION"));
selArticle.setWhere(new Where(tableArticle.getField("OBSOLETE"), "=", Boolean.FALSE).and(new Where(tableArticle.getField("MASQUE_CAISSE"), "=", Boolean.FALSE)));
selArticle.andWhere(new Where(tableArticle.getField("VIRTUEL"), "=", Boolean.FALSE));
 
333,6 → 335,15
}
}
 
final SQLSelect selArtVirt = new SQLSelect();
selArtVirt.addSelect(tableArticle.getKey());
selArtVirt.addSelect(tableArticle.getField("NOM"));
 
Map<Integer, String> mapVirtuel = new HashMap<>();
for (SQLRow row : SQLRowListRSH.execute(selArtVirt)) {
mapVirtuel.put(row.getID(), row.getString("NOM"));
}
 
final Categorie cUnclassified = new Categorie("Non classés", true);
cUnclassified.setUnknown();
 
339,16 → 350,17
// Fetch des declinaisons :
// "ID_ARTICLE_DECLINAISON_COULEUR" : { {3 , "noir"] } ,
// "ID_ARTICLE_DECLINAISON_TAILLE" : { {2 ,"XL"},{3,"XXL"}};
Map<String, Map<Integer, String>> mapDeclinaisons = new HashMap<>();
Map<String, Map<Integer, Tuple2<String, BigDecimal>>> mapDeclinaisons = new HashMap<>();
for (String table : tablesDeclinaisons) {
SQLTable t = eltArticle.getTable().getTable(table);
final SQLSelect selDecl = new SQLSelect();
selDecl.addSelect(t.getKey());
selDecl.addSelect(t.getField("NOM"));
Map<Integer, String> m = new HashMap<>();
selDecl.addSelect(t.getField("ORDRE"));
Map<Integer, Tuple2<String, BigDecimal>> m = new HashMap<>();
mapDeclinaisons.put("ID_" + table, m);
for (SQLRow row : SQLRowListRSH.execute(selDecl)) {
m.put(row.getID(), row.getString("NOM"));
m.put(row.getID(), Tuple2.create(row.getString("NOM"), row.getBigDecimal("ORDRE")));
}
}
// Fetch des articles
384,7 → 396,7
Map<Integer, List<TarifQuantite>> mapTarif = new HashMap<>();
System.err.println("CaissePanel.loadArticles()" + rPromotions.size() + " promotions");
for (SQLRowValues r : rPromotions) {
final Integer foreignID = ((Integer) r.getObjectNoCheck("ID_ARTICLE"));
final Integer foreignID = r.getForeignID("ID_ARTICLE");
List<TarifQuantite> list = mapTarif.get(foreignID);
if (list == null) {
list = new ArrayList<>();
442,11 → 454,15
for (String f : declinaisonsFieldNames) {
Integer idArtDeclinaison = (Integer) row.getObjectNoCheck(f);
if (idArtDeclinaison != null && idArtDeclinaison > 1) {
Map<Integer, String> mm = mapDeclinaisons.get(f);
Map<Integer, Tuple2<String, BigDecimal>> mm = mapDeclinaisons.get(f);
if (mm != null) {
String v = mm.get(idArtDeclinaison);
a.addDeclinaison(f.substring("ID_ARTICLE_DECLINAISON_".length()), v);
Tuple2<String, BigDecimal> v = mm.get(idArtDeclinaison);
a.addDeclinaison(f.substring("ID_ARTICLE_DECLINAISON_".length()), v.get0(), v.get1());
}
// Integer pere = (Integer) row.getObjectNoCheck("ID_ARTICLE_VIRTUEL_PERE");
// if (pere != null && mapVirtuel.containsKey(pere)) {
// a.setArticlePereNom(mapVirtuel.get(pere));
// }
}
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/TicketCellRenderer.java
17,6 → 17,7
import org.openconcerto.erp.core.sales.pos.model.TicketItem;
import org.openconcerto.ui.touch.ScrollableList;
import org.openconcerto.utils.QuickOrderedMap;
import org.openconcerto.utils.Tuple2;
 
import java.awt.Color;
import java.awt.Component;
112,12 → 113,12
if (s2.length() > maxLength) {
s2 = s2.substring(0, maxLength + 1) + '…';
}
QuickOrderedMap<String, String> decls = article.getDeclinaisons();
QuickOrderedMap<String, Tuple2<String, BigDecimal>> decls = article.getDeclinaisons();
String textDeclinaisons = null;
if (decls != null && !decls.isEmpty()) {
StringBuilder declinaisons = new StringBuilder();
for (int i = 0; i < decls.size(); i++) {
declinaisons.append(decls.getValue(i));
declinaisons.append(decls.getValue(i).get0());
declinaisons.append(" ");
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/StockErrorPanel.java
35,6 → 35,7
import java.util.Map;
 
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
 
public class StockErrorPanel extends JPanel {
private final CaisseControler controller;
80,24 → 81,25
final SQLSelect select = new SQLSelect();
select.addSelect(tDepot.getField("ID"));
select.addSelect(tDepot.getField("NOM"));
for (final SQLRow rowDepotArrivee : SQLRowListRSH.execute(select)) {
final int idDepotSource = rowDepotArrivee.getInt("ID");
final String nomDepot = rowDepotArrivee.getString("NOM");
int nbChoice = 0;
for (final SQLRow rowDepotDepart : SQLRowListRSH.execute(select)) {
final int idDepotDepart = rowDepotDepart.getInt("ID");
final String nomDepotDepart = rowDepotDepart.getString("NOM");
final int idDepotIDestination = caisseFrame.getPOSConf().getDepotID();
if (idDepotSource != idDepotIDestination) {
POSButton b = new POSButton("Créer un mouvement de stock depuis le dépôt " + nomDepot);
if (idDepotDepart != idDepotIDestination) {
POSButton b = new POSButton("Créer un mouvement de stock depuis le dépôt " + nomDepotDepart);
b.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent ev) {
System.err.println("StockErrorPanel.StockErrorPanel(...) mouvement de stock");
final SQLRow selectedRowDepotDepart = tDepot.getRow(idDepotSource);
final SQLRow selectedRowDepotArrivee = tDepot.getRow(idDepotIDestination);
final Date date = new Date();
for (Map.Entry<TicketItem, Integer> e : missingQty.entrySet()) {
final int idArticle = e.getKey().getArticle().getId();
final BigDecimal qteReel = new BigDecimal(e.getValue());
final SQLRow selectedRowArticle = tArticle.getRow(idArticle);
dir.getElement(MouvementStockSQLElement.class).transfertStock(qteReel, date, selectedRowArticle, selectedRowDepotDepart, rowDepotArrivee, "transfert depuis caisse");
dir.getElement(MouvementStockSQLElement.class).transfertStock(qteReel, date, selectedRowArticle, rowDepotDepart, selectedRowDepotArrivee, "transfert depuis caisse");
}
caisseFrame.showCaisse();
runnable.run();
105,21 → 107,21
});
c.gridy++;
this.add(b, c);
nbChoice++;
}
}
POSButton b = new POSButton("Ignorer le problème de stock");
b.addActionListener(new ActionListener() {
if (nbChoice == 0) {
SwingUtilities.invokeLater(new Runnable() {
 
@Override
public void actionPerformed(ActionEvent e) {
System.err.println("StockErrorPanel.StockErrorPanel(...) ignore stock");
public void run() {
caisseFrame.showCaisse();
runnable.run();
 
}
});
c.gridy++;
this.add(b, c);
 
} else {
 
POSButton b2 = new POSButton("Annuler la validation du ticket");
b2.addActionListener(new ActionListener() {
 
133,5 → 135,6
c.gridy++;
this.add(b2, c);
}
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/CaisseControler.java
14,6 → 14,8
package org.openconcerto.erp.core.sales.pos.ui;
 
import org.openconcerto.erp.core.sales.pos.POSConfiguration;
import org.openconcerto.erp.core.sales.pos.io.Barcode;
import org.openconcerto.erp.core.sales.pos.io.BarcodeListener;
import org.openconcerto.erp.core.sales.pos.io.BarcodeReader;
import org.openconcerto.erp.core.sales.pos.io.ESCSerialDisplay;
import org.openconcerto.erp.core.sales.pos.io.TicketPrinter;
251,7 → 253,8
}
 
@Override
public void barcodeRead(String code) {
public void barcodeRead(Barcode barcode) {
String code = barcode.getData();
System.err.println("CaisseControler.barcodeRead() barcode : " + code);
if (code.equalsIgnoreCase("especes")) {
autoFillPaiement(this.p1);
468,8 → 471,6
return (!this.t.getItems().isEmpty()) && ((this.getTotal() >= 0 && this.getPaidTotal() >= this.getTotal()) || (this.getTotal() < 0 && this.getPaidTotal() == this.getTotal()));
}
 
 
public void setTicketItemSelected(TicketItem item) {
this.ticketItemSelected = item;
if (item == null) {
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/ui/TicketClientNamePanel.java
25,6 → 25,7
import java.awt.event.ActionListener;
import java.util.Collections;
 
import javax.swing.JButton;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
67,9 → 68,11
tAdresse.setText(ticket.getClient().getAddr());
this.add(new JScrollPane(tAdresse), c);
c.gridy++;
final JButton b;
c.fill = GridBagConstraints.NONE;
// Textfield
POSButton b = new POSButton("Imprimer");
c.fill = GridBagConstraints.NONE;
if (caisseFrame != null) {
b = new POSButton("Imprimer");
b.addActionListener(new ActionListener() {
 
@Override
78,9 → 81,23
ticket.getClient().setAdresse(tAdresse.getText());
printInvoice(ticket);
caisseFrame.showCaisse();
}
});
} else {
b = new JButton("Imprimer");
c.fill = GridBagConstraints.NONE;
b.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
ticket.getClient().setFullName(text.getText());
ticket.getClient().setAdresse(tAdresse.getText());
printInvoice(ticket);
SwingUtilities.getWindowAncestor(TicketClientNamePanel.this).dispose();
 
}
});
}
c.gridy++;
this.add(b, c);
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/model/Article.java
16,6 → 16,7
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.QuickOrderedMap;
import org.openconcerto.utils.Tuple2;
 
import java.math.BigDecimal;
import java.math.RoundingMode;
42,10 → 43,13
private String salesUnit;
private static Map<String, List<Article>> codes = new HashMap<>();
 
// declinaison (ex "taille":"45", "couleur","rouge"), null si pas de declinaison
private QuickOrderedMap<String, String> declinaisons;
// type de declinaison : nom de la déclinaison et ordre (ex "taille":"45 / 5.5",
// "couleur","rouge / 2.05"), null si pas de declinaison
private QuickOrderedMap<String, Tuple2<String, BigDecimal>> declinaisons;
 
List<TarifQuantite> tarifs;
private String declinaison;
private String articlePereNom = null;
 
public Article(Categorie s1, String string, int id) {
this.s = s1;
68,7 → 72,7
this.ecotaxe = a.ecotaxe;
 
this.s.addArticle(this);
final QuickOrderedMap<String, String> decl = a.getDeclinaisons();
final QuickOrderedMap<String, Tuple2<String, BigDecimal>> decl = a.getDeclinaisons();
if (decl != null) {
final int size = decl.size();
this.declinaisons = new QuickOrderedMap<>(size);
109,17 → 113,25
return result;
}
 
public void addDeclinaison(String key, String value) {
public void addDeclinaison(String key, String value, BigDecimal ordreDeclinaison) {
if (this.declinaisons == null) {
this.declinaisons = new QuickOrderedMap<>(5);
}
this.declinaisons.put(key, value);
this.declinaisons.put(key, Tuple2.create(value, ordreDeclinaison));
}
 
public QuickOrderedMap<String, String> getDeclinaisons() {
public QuickOrderedMap<String, Tuple2<String, BigDecimal>> getDeclinaisons() {
return this.declinaisons;
}
 
public void setArticlePereNom(String articlePereNom) {
this.articlePereNom = articlePereNom;
}
 
public String getArticlePereNom() {
return this.articlePereNom;
}
 
public boolean isPromotion() {
return this.tarifs != null && !this.tarifs.isEmpty();
}
238,7 → 250,8
if (this.declinaisons != null) {
return "Article:" + this.code + " | " + this.name + " " + this.priceTTC + " cents" + "(HT:" + this.priceHT + ") " + getSalesUnit() + " discount:" + getDiscountPct();
}
return "Article:" + this.code + " | " + this.name + " [" + this.declinaisons + "] : " + this.priceTTC + " cents" + "(HT:" + this.priceHT + ") " + getSalesUnit() + " discount:" + getDiscountPct();
return "Article:" + this.code + " | " + this.name + " [" + this.declinaisons + "] : " + this.priceTTC + " cents" + "(HT:" + this.priceHT + ") " + getSalesUnit() + " discount:"
+ getDiscountPct();
}
 
public static List<Article> getArticleFromBarcode(String code) {
307,9 → 320,12
if (this.declinaison == null && this.declinaisons != null && !this.declinaisons.isEmpty()) {
StringBuilder b = new StringBuilder();
for (int i = 0; i < this.declinaisons.size(); i++) {
b.append(this.declinaisons.getValue(i));
final Tuple2<String, BigDecimal> value = this.declinaisons.getValue(i);
if (value != null) {
b.append(value.get0());
b.append(" ");
}
}
 
return b.toString().trim();
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/model/Categorie.java
13,6 → 13,10
package org.openconcerto.erp.core.sales.pos.model;
 
import org.openconcerto.utils.QuickOrderedMap;
import org.openconcerto.utils.Tuple2;
 
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
103,9 → 107,29
Collections.sort(result, new Comparator<Article>() {
@Override
public int compare(Article o1, Article o2) {
final boolean isChild = o1.getArticlePereNom() != null && o2.getArticlePereNom() != null && o1.getArticlePereNom().trim().length() > 0
&& o1.getArticlePereNom().equals(o2.getArticlePereNom());
final QuickOrderedMap<String, Tuple2<String, BigDecimal>> declinaisons1 = o1.getDeclinaisons();
final QuickOrderedMap<String, Tuple2<String, BigDecimal>> declinaisons2 = o2.getDeclinaisons();
final boolean hasDecl = isChild && declinaisons1 != null && !declinaisons1.isEmpty() && declinaisons2 != null && !declinaisons2.isEmpty();
if (o1.getName().compareTo(o2.getName()) == 0 && hasDecl) {
for (int i = 0; i < declinaisons1.size(); i++) {
final String key = declinaisons1.getKey(i);
final Tuple2<String, BigDecimal> tuple1 = declinaisons1.get(key);
final Tuple2<String, BigDecimal> tuple2 = declinaisons2.get(key);
if (tuple1 != null && tuple2 != null) {
BigDecimal order1 = tuple1.get1();
BigDecimal order2 = tuple2.get1();
if (order1.compareTo(order2) != 0) {
return order1.compareTo(order2);
}
}
}
}
return o1.getName().compareTo(o2.getName());
}
});
 
return result;
}
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/io/Barcode.java
New file
0,0 → 1,255
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.pos.io;
 
public class Barcode {
 
public enum BarcodeType {
CODE39, TELEPEN, CODE128, EAN, CODABAR, CODE93, CODE11, PDF417, MSIPLESSEY, QRCODE, DATAMATRIX, GS1, UNKNOWN
}
 
public static final String AIM_PREFIX_CODE39_NOCHECK = "]A0";// Code39 No check character nor
// Full ASCII processing.
 
public static final String AIM_PREFIX_CODE39_CHECKED = "]A1"; // Code39 Reader has performed mod
// 43 check and transmitted
public static final String AIM_PREFIX_CODE39_CHECKED_STRIPPED = "]A2";// Code39 Reader has
// performed mod
// 43 check and stripped the check
// character
public static final String AIM_PREFIX_CODE39_ASCII = "]A4";// Code39 Reader has performed Full
// ASCII conversion. No check
// character validation
public static final String AIM_PREFIX_CODE39_ASCII_CHECKED = "]A5"; // Code39 Reader has
// performed
// Full ASCII character
// conversion, verfied check
// character and transmitted it.
public static final String AIM_PREFIX_CODE39_ASCII_STRIPPED = "]A7"; // Code39 Reader has
// performed
// Full ASCII character
// conversion, verified check
// character and stripped it.
public static final String AIM_PREFIX_TELEPEN_ASCII = "]B0"; // Telepen Full ASCII mode
public static final String AIM_PREFIX_TELEPEN_DD = "]B1"; // Telepen Double density numeric
// mode
public static final String AIM_PREFIX_TELEPEN_DD_ASCII = "]B2"; // Telepen Double density
// numeric
// followed by full ASCII
public static final String AIM_PREFIX_TELEPEN_ASCII_DD = "]B4"; // Telepen Full ASCII followed
// by
// double density numeric
public static final String AIM_PREFIX_CODE128 = "]C0"; // Code128 Standard. No FNC1 in
// first or second symbol
// character position after start
// character.
public static final String AIM_PREFIX_CODE128_C1 = "]C1"; // Code128 Function code 1 in
// first character position or GS1
// Databar Expanded
public static final String AIM_PREFIX_CODE128_C2 = "]C2"; // Code128 Function code 2 in
// second character position.
// Concatenation according to ISBT
public static final String AIM_PREFIX_CODE128_ISBT = "]C4"; // Code128 Concatenation according
// to ISBT (International Society
// for Blood Transfusion)
// specification has been
// performed,
// and concatenated data follows. AKA ISBT-128
public static final String AIM_PREFIX_EAN = "]E0"; // UPC/EAN Standard packet in full
// EAN country code format, which
// is 13 digits for UPC-A and
// UPC-E
// (not including supplemental data) or Bookland EAN.
public static final String AIM_PREFIX_EAN_2S = "]E1"; // UPC/EAN Two-digit supplement
// data only.
public static final String AIM_PREFIX_EAN_5S = "]E2"; // UPC/EAN Five-digit supplement
// data only.
public static final String AIM_PREFIX_EAN_25S = "]E3"; // EAN-13 with 2/5-Digit Add-On
// Code or UPC-E with 2/5-Digit
// Add-On / Extended Coupon Code /
// EAN-8 with Add-On
public static final String AIM_PREFIX_EAN8 = "]E4"; // EAN-8 EAN-8
public static final String AIM_PREFIX_CODABAR = "]F0"; // Codabar No check digit
// processing.
public static final String AIM_PREFIX_CODABAR_CHECKED = "]F1"; // Codabar Reader has checked
// check digit and check digit is
// transmitted.
// ABC (American Blood Commission) Codabar concatenate/message append performed.
public static final String AIM_PREFIX_CODABAR_VALIDATED = "]F3"; // Codabar Reader has validated
// check digit and sends it.
public static final String AIM_PREFIX_CODABAR_VALIDATED_STRIPPED = "]F3"; // Codabar Reader has
// validated
// and stripped check digit before
// transmission.
public static final String AIM_PREFIX_CODE93 = "]G0"; // Code93 Possible modifiers might
// be 0-9, A-Z, a-m... <tag
// name="todo">@todo</tag>
public static final String AIM_PREFIX_CODE11_SD = "]H0"; // Code11 Single check digit
// validated and transmitted
public static final String AIM_PREFIX_CODE11_TD = "]H1"; // Code11 Two check digits
// validated and transmitted
public static final String AIM_PREFIX_CODE11_CHECKED = "]H3"; // Code11 Check characters
// validated but not transmitted
 
public static final String AIM_PREFIX_PDF417 = "]L0"; // PDF417 Reader set to conform
// with protocol defined in 1994
// PDF417 symbology
// specifications.
// When this option is transmitted, the receiver cannot determine reliably whether ECIs have
// bebb invoked,
// nor whether data byte 92 has been doubled in transmission.
public static final String AIM_PREFIX_PDF417_ENV12925 = "]L1"; // PDF417 Reader set follow the
// protocol of this standard for
// ENV 12925 for Extended Channel
// Interpretation.
// All data characters 92 are doubled.
public static final String AIM_PREFIX_PDF417_BASIC = "]L2"; // PDF417 Reader set follow the
// protocol of this standard for
// Basic Chanel operation. Data
// characters 92 are not doubled.
// When decoders are set to this mode, unbuffered Structured Append symbols and symbols
// requiring the decoded by convey ECI
// sequences cannot be transmitted or TCIF Linked Code39 (TLC39)
public static final String AIM_PREFIX_PDF417_CODE128_FNC1_1 = "]L3"; // PDF417 Code 128
// emulation :
// implied FNC1 in first position
// (only applicable for Micro
// PDF417)
public static final String AIM_PREFIX_PDF417_CODE128_FNC1_2 = "]L4"; // PDF417 Code 128
// emulation :
// implied FNC1 after initial
// letter or pair odf digits (only
// applicable for Micro PDF417)
public static final String AIM_PREFIX_PDF417_CODE128 = "]L5"; // PDF417 Code 128 emulation: no
// implied FNC1 (only applicable
// for Micro PDF417)
public static final String AIM_PREFIX_MSI_PLESSEY = "]M0"; // MSI Plessey Check digits are
// sent.
 
public static final String AIM_PREFIX_MSI_PLESSEY_2 = "]M1"; // MSI Plessey Two check digits
// checked.
 
public static final String AIM_PREFIX_QRCODE_1 = "]Q0"; // QR Code Model 1 symbol.
public static final String AIM_PREFIX_QRCODE_2 = "]Q1"; // QR Code Model 2 (QR Code 2005),
// ECI protocol **not**
// implemented.
public static final String AIM_PREFIX_QRCODE_2_ECI = "]Q2"; // QR Code Model 2 (QR Code 2005),
// ECI protocol implemented.
public static final String AIM_PREFIX_QRCODE_2_FNC1 = "]Q3"; // QR Code Model 2 (QR Code 2005),
// ECI protocol **not**
// implemented, FNC1 implied in
// first position.
public static final String AIM_PREFIX_QRCODE_2_FNC1_ECI = "]Q4"; // QR Code Model 2 (QR Code
// 2005),
// ECI protocol implemented,
// FNC1
// implied in first position.
public static final String AIM_PREFIX_QRCODE_2_FNC1_2 = "]Q5"; // QR Code Model 2 (QR Code
// 2005),
// ECI protocol **not**
// implemented, FNC1 implied in
// second position.
public static final String AIM_PREFIX_QRCODE_2_FNC1_2_ECI = "]Q6"; // QR Code Model 2 (QR Code
// 2005),
// ECI protocol implemented, FNC1
// implied in second position.
 
public static final String AIM_PREFIX_NO_BARECODE = "]Z"; // - This means: No barcode data
public static final String AIM_PREFIX_DATAMATRIX_ECC140 = "]d0"; // Data Matrix ECC 000-140.
public static final String AIM_PREFIX_DATAMATRIX_ECC200 = "]d1"; // Data Matrix ECC 200.
public static final String AIM_PREFIX_DATAMATRIX_ECC200_FNC1_1 = "]d2"; // Data Matrix ECC 200,
// FNC1 in
// first or fifth position.
public static final String AIM_PREFIX_DATAMATRIX_ECC200_FNC1_2 = "]d3"; // Data Matrix ECC 200,
// FNC1 in
// second or sixth position.
public static final String AIM_PREFIX_DATAMATRIX_ECC200_ECI = "]d4"; // Data Matrix ECC 200, ECI
// protocol implemented.
public static final String AIM_PREFIX_DATAMATRIX_ECC200_FNC1_1_ECI = "]d5"; // Data Matrix ECC
// 200, FNC1 in
// first or fifth position, ECI
// protocol implemented.
public static final String AIM_PREFIX_DATAMATRIX_ECC200_FNC1_2_ECI = "]d6"; // Data Matrix ECC
// 200, FNC1 in
// second or sixth position, ECI
// protocol implemented.
public static final String AIM_PREFIX_DATAMATRIX_GS1 = "]e0"; // GS1 GS1 DataBar / GS1 DataBar
// Limited / GS1 Databar Expanded
public static final String AIM_PREFIX_DATAMATRIX_GS1_SEP = "]e1"; // GS1 Contains data following
// an
// encoded symbol separator
// character.
public static final String AIM_PREFIX_DATAMATRIX_GS1_ESC = "]e2"; // GS1 Contains data following
// an
// escape mechanism character. The
// data packet does **not**
// support the ECI protocol.
public static final String AIM_PREFIX_DATAMATRIX_GS1_ESC_ECI = "]e3"; // GS1 Contains data
// following an
// escape mechanism character. The
// data packet supports the ECI
// protocol.
private String code;
 
/**
* Barcode from scanner (read characters)
*/
public Barcode(String code) {
this.code = code;
}
 
public String getCode() {
return code;
}
 
public String getData() {
if (this.code.length() > 3 && this.getType() != BarcodeType.UNKNOWN) {
return this.code.substring(3);
}
return this.code;
}
 
public BarcodeType getType() {
if (this.code.length() > 3 && this.code.charAt(0) == ']') {
char c = this.code.charAt(1);
if (c == 'A') {
return BarcodeType.CODE39;
} else if (c == 'B') {
return BarcodeType.TELEPEN;
} else if (c == 'C') {
return BarcodeType.CODE128;
} else if (c == 'E') {
return BarcodeType.EAN;
} else if (c == 'F') {
return BarcodeType.CODABAR;
} else if (c == 'G') {
return BarcodeType.CODE93;
} else if (c == 'H') {
return BarcodeType.CODE11;
} else if (c == 'L') {
return BarcodeType.PDF417;
} else if (c == 'M') {
return BarcodeType.MSIPLESSEY;
} else if (c == 'Q') {
return BarcodeType.QRCODE;
} else if (c == 'd') {
return BarcodeType.DATAMATRIX;
} else if (c == 'e') {
return BarcodeType.GS1;
}
}
return BarcodeType.UNKNOWN;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/io/BarcodeReader.java
13,32 → 13,49
package org.openconcerto.erp.core.sales.pos.io;
 
import org.openconcerto.erp.core.sales.pos.ui.BarcodeListener;
import org.openconcerto.erp.gs1.GS1Util;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.ui.component.ITextArea;
import org.openconcerto.utils.StringUtils;
 
import java.awt.Color;
import java.awt.Component;
import java.awt.Desktop;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.KeyEventDispatcher;
import java.awt.KeyboardFocusManager;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Timer;
import java.util.TimerTask;
 
import javax.swing.JButton;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JSpinner;
import javax.swing.JTable;
import javax.swing.JTextArea;
import javax.swing.SpinnerNumberModel;
import javax.swing.SwingUtilities;
import javax.swing.UIManager;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.swing.event.TableModelEvent;
import javax.swing.event.TableModelListener;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.TableModel;
 
/**
* Lecteur code barres, intercepte les événements clavier pour détecter un scan de code. Le code
47,35 → 64,186
*/
public class BarcodeReader implements KeyEventDispatcher {
 
public int maxInterKeyDelay = 80;
public class KeyEventTableModel implements TableModel {
public static final String CHAR_UNDEFINED = "CHAR_UNDEFINED";
public static final String KEY_TYPED = "Key Typed";
List<TableModelListener> listeners = new ArrayList<>();
List<KeyEvent> list = new ArrayList<>();
 
private KeyEventTableModel() {
//
}
 
@Override
public int getRowCount() {
return list.size();
}
 
@Override
public int getColumnCount() {
return 4;
}
 
@Override
public String getColumnName(int columnIndex) {
switch (columnIndex) {
case 0:
return "Date";
case 1:
return "ID";
case 2:
return "Code";
case 3:
return "Character";
default:
break;
}
return "?";
}
 
@Override
public Class<?> getColumnClass(int columnIndex) {
if (columnIndex == 0) {
return Date.class;
}
return String.class;
}
 
@Override
public boolean isCellEditable(int rowIndex, int columnIndex) {
return false;
}
 
@Override
public Object getValueAt(int rowIndex, int columnIndex) {
KeyEvent e = list.get(rowIndex);
switch (columnIndex) {
case 0:
return new Date(e.getWhen());
case 1:
int id = e.getID();
if (id == KeyEvent.KEY_TYPED) {
return KEY_TYPED;
}
if (id == KeyEvent.KEY_PRESSED) {
return "Key Pressed";
}
if (id == KeyEvent.KEY_RELEASED) {
return "Key Released";
}
return String.valueOf(id);
case 2:
int code = e.getKeyCode();
String name = "";
if (code == KeyEvent.VK_ENTER) {
name = "ENTER";
} else if (code == KeyEvent.VK_BACK_SPACE) {
name = "BACK SPACE";
} else if (code == KeyEvent.VK_SHIFT) {
name = "SHIFT";
} else if (code >= KeyEvent.VK_0 && code <= KeyEvent.VK_9) {
name = "DIGIT";
} else if (code >= KeyEvent.VK_A && code <= KeyEvent.VK_Z) {
name = "CHAR";
} else if (code == KeyEvent.VK_F8) {
name = "F8";
}
return (name + " " + String.valueOf(code) + " 0x" + charToHex((char) code)).trim();
case 3:
char kc = e.getKeyChar();
if (kc == KeyEvent.CHAR_UNDEFINED) {
return CHAR_UNDEFINED;
} else if (kc == 29) {
return "<GS>";
}
return String.valueOf(kc);
default:
break;
}
 
return null;
}
 
@Override
public void setValueAt(Object aValue, int rowIndex, int columnIndex) {
// nothing
 
}
 
@Override
public void addTableModelListener(TableModelListener l) {
this.listeners.add(l);
 
}
 
@Override
public void removeTableModelListener(TableModelListener l) {
this.listeners.remove(l);
}
 
Timer t = new Timer();
 
public void fire() {
t.cancel();
t = new Timer();
t.schedule(new TimerTask() {
 
@Override
public void run() {
for (TableModelListener l : listeners) {
l.tableChanged(new TableModelEvent(KeyEventTableModel.this));
}
 
}
}, 400);
 
}
 
public void clear() {
this.list.clear();
fire();
}
 
public void add(KeyEvent e) {
this.list.add(e);
fire();
 
}
 
}
 
private int maxInterKeyDelay = 200;
private static final int MIN_BARCODE_LENGTH = 2;
private final List<BarcodeListener> listeners = new ArrayList<BarcodeListener>(1);
private final List<BarcodeListener> listeners = new ArrayList<>(1);
private List<KeyEventDispatcher> dispatchers = null;
private String value = "";
private final List<KeyEvent> eve = new ArrayList<KeyEvent>();
private final List<KeyEvent> eve = new ArrayList<>();
private long firstTime = -1;
private Timer timer;
// non final car un TimerTask n'est pas reutilisable
private TimerTask task;
private boolean enable = true;
private boolean debug = false;
private Map<Integer, String> mapCharacterFR = new HashMap<>();
private boolean debug = true;
private List<Integer> valueCode = new ArrayList<>();
 
public BarcodeReader(int maxInterKeyDelay) {
this.timer = null;
this.task = null;
this.maxInterKeyDelay = maxInterKeyDelay;
this.mapCharacterFR.put((int) '&', "1");
this.mapCharacterFR.put((int) 'é', "2");
this.mapCharacterFR.put((int) '"', "3");
this.mapCharacterFR.put((int) '\'', "4");
this.mapCharacterFR.put((int) '(', "5");
this.mapCharacterFR.put((int) '-', "6");
this.mapCharacterFR.put((int) 'è', "7");
this.mapCharacterFR.put((int) '_', "8");
this.mapCharacterFR.put((int) 'ç', "9");
this.mapCharacterFR.put((int) 'à', "0");
 
}
 
public void setMaxInterKeyDelay(int maxInterKeyDelay) {
this.maxInterKeyDelay = maxInterKeyDelay;
}
 
public void addKeyEventDispatcher(KeyEventDispatcher d) {
if (this.dispatchers == null) {
this.dispatchers = new ArrayList<>();
}
this.dispatchers.add(d);
}
 
public synchronized void removeBarcodeListener(BarcodeListener l) {
this.listeners.remove(l);
if (this.listeners.isEmpty()) {
90,7 → 258,7
this.listeners.add(l);
}
 
private void fire(String code) {
private void fire(Barcode code) {
for (int i = 0; i < this.listeners.size(); i++) {
this.listeners.get(i).barcodeRead(code);
}
105,7 → 273,7
// init avant que les listeners s'en servent
this.timer = new Timer(getClass().getName(), true);
KeyboardFocusManager.getCurrentKeyboardFocusManager().addKeyEventDispatcher(this);
System.err.println("BarcodeReader start : scan delay " + this.maxInterKeyDelay + " ms");
System.err.println("BarcodeReader start : scan delay between keys" + this.maxInterKeyDelay + " ms");
}
}
 
121,6 → 289,8
}
}
 
int lastPressedkeyCode = 0;
 
@Override
public boolean dispatchKeyEvent(KeyEvent e) {
if (!this.enable) {
128,11 → 298,17
}
if (this.task != null)
this.task.cancel();
if (this.dispatchers != null) {
for (KeyEventDispatcher d : this.dispatchers) {
d.dispatchKeyEvent(e);
}
}
 
final long t = e.getWhen();
if (this.firstTime < 0) {
this.firstTime = t;
}
 
int keyCode = e.getKeyCode();
 
final long delay = t - this.firstTime;
139,7 → 315,7
if (keyCode == KeyEvent.VK_BACK_SPACE || keyCode == KeyEvent.VK_DELETE || (delay > this.maxInterKeyDelay && keyCode != KeyEvent.VK_SHIFT)) {
// touche normale
if (this.debug) {
System.err.println("Touche normale " + keyCode);
System.err.println("Touche normale " + keyCode + " delai:" + delay);
}
this.eve.add(e);
redispatch();
148,63 → 324,173
 
final char keyChar = e.getKeyChar();
this.eve.add(e);
if (e.getID() == KeyEvent.KEY_RELEASED) {
if (keyCode == KeyEvent.VK_SHIFT) {
// rien
if (this.debug) {
System.err.println("SHIFT " + keyCode);
if (e.getID() == KeyEvent.KEY_PRESSED) {
lastPressedkeyCode = e.getKeyCode();
}
} else if (keyChar == ']') {
this.value += keyChar;
if (this.debug) {
System.err.println("]");
}
} else if (keyChar == '*' || keyChar == '$' || keyChar == '+' || keyChar == '/' || keyChar == '%' || keyChar == ' ') {
this.value += keyChar;
if (this.debug) {
System.err.println("KEY " + keyCode + " - " + keyChar);
}
} else if (keyCode >= KeyEvent.VK_0 && keyCode <= KeyEvent.VK_9 || keyCode >= KeyEvent.VK_A && keyCode <= KeyEvent.VK_Z) {
// from KeyEvent : same as ASCII
if (this.debug) {
System.err.println("[0-9] [A-Z] " + keyCode + " : " + keyChar);
}
this.value += (char) keyCode;
} else if (keyCode == KeyEvent.VK_ENTER && this.value.length() >= MIN_BARCODE_LENGTH) {
if (e.getID() == KeyEvent.KEY_RELEASED && keyCode == KeyEvent.VK_F8) {
this.value += '\u001D';
this.valueCode.add(lastPressedkeyCode);
} else {
if (e.getID() == KeyEvent.KEY_RELEASED && keyCode == KeyEvent.VK_ENTER && this.value.length() >= MIN_BARCODE_LENGTH) {
// fin de code barre
if (this.debug) {
System.err.println("BARCODE OK ENTER OR LENGHT " + keyCode + " length = " + this.value.length() + " min length =" + MIN_BARCODE_LENGTH);
}
this.value = this.value.trim();
fire(this.value);
reset();
} else if (this.mapCharacterFR.containsKey((int) keyChar)) {
if (this.debug) {
System.err.println("MAP DEFAULT FR CHAR " + keyChar + " WITH " + this.mapCharacterFR.get((int) keyChar));
if (this.value.startsWith("$")) {
// Barcode not configured for FR
StringBuilder b = new StringBuilder(this.value.length());
for (int i = 0; i < this.value.length(); i++) {
char c = this.value.charAt(i);
int kCode = this.valueCode.get(i);
if (c == '&') {
b.append('1');
} else if (c == 'é') {
b.append('2');
} else if (c == '"') {
b.append('3');
} else if (c == '\'') {
b.append('4');
} else if (c == '(') {
b.append('5');
} else if (c == '-') {
if (kCode == 109) {
b.append('-');
} else {
b.append('6');
}
this.value += this.mapCharacterFR.get((int) keyChar);
} else if (Character.isLetter(keyChar) || Character.isDigit(keyChar)) {
this.value += keyChar;
if (this.debug) {
System.err.println("LETTER OR DIGIT " + keyChar);
} else if (c == 'è') {
 
b.append('7');
 
} else if (c == '_') {
b.append('8');
} else if (c == 'ç') {
b.append('9');
} else if (c == 'à') {
b.append('0');
} else if (c == '$') {
b.append(']');
} else if (c == 'M') {
b.append(':');
} else if (c == '!') {
b.append('/');
} else if (c == 'q') {
b.append('a');
} else if (c == 'a') {
b.append('q');
} else if (c == 'z') {
b.append('w');
} else if (c == 'w') {
b.append('z');
} else if (c == 'Q') {
b.append('A');
} else if (c == 'A') {
b.append('Q');
} else if (c == 'Z') {
b.append('W');
} else if (c == 'W') {
b.append('Z');
} else if (c == ',') {
b.append('m');
} else if (c == '?') {
b.append('M');
} else if (c == ':') {
b.append('.');
} else if (c == 'Ò') {
b.append('°');
} else if (c == 'ª') {
b.append('é');
} else if (c == '%') {
b.append('"');
} else if (c == 'ù') {
b.append('\'');
} else if (c == '¨') {
b.append('{');
} else if (c == '£') {
b.append('}');
} else if (c == 'ñ') {
if (kCode == 18) {
b.append('à');
} else
b.append('&');
} else if (c == '0') {
b.append(')');
} else if (c == '1') {
b.append('!');
} else if (c == '2') {
b.append('@');
} else if (c == '3') {
b.append('#');
} else if (c == '4') {
b.append('$');
} else if (c == '5') {
b.append('%');
} else if (c == '6') {
if (kCode == 54) {
b.append('^');
} else
b.append('ç');
} else if (c == '7') {
//
b.append('&');
} else if (c == '9') {
b.append('(');
} else if (c == '^') {
b.append('[');
} else if (c == 'µ') {
b.append('|');
} else if (c == '¿') {
b.append('è');
} else if (c == '²') {
b.append('`');
} else if (c == '°') {
b.append('_');
} else if (c == '/') {
b.append('>');
} else if (c == '.') {
b.append('<');
} else if (c == 'ý') {
b.append('§');
} else if (c == 'm') {
b.append(';');
} else if (c == '┤') {
b.append('ù');
} else if (c == '\\') {
b.append('*');
} else if (c == '§') {
b.append('?');
} else if (c == ';') {
b.append(',');
} else if (c == '*') {
if (kCode == 106) {
b.append('*');
} else
b.append('\\');
} else {
b.append(c);
}
} else if (keyChar == 29) {
this.value += '\u001D';
if (this.debug) {
System.err.println("<GS>");
 
}
} else if (keyChar == KeyEvent.CHAR_UNDEFINED) {
System.err.println("CHAR_UNDEFINED");
this.value += '\u001D';
this.value = b.toString();
fire(new Barcode(this.value));
} else {
// Caractere non code barre
if (this.debug) {
System.err.println("CHAR NON CODE BARRE keyCode:" + keyCode + " keyChar:" + keyChar);
fire(new Barcode(this.value));
}
redispatch();
reset();
} else if (e.getID() == KeyEvent.KEY_TYPED) {
this.value += keyChar;
this.valueCode.add(lastPressedkeyCode);
}
 
}
 
// redispatch();
 
// lance un timer s'il reste des evenements non dispatchés
if (!this.eve.isEmpty()) {
if (!this.eve.isEmpty())
 
{
this.firstTime = t;
this.task = new TimerTask() {
@Override
225,7 → 511,7
}
// si pas d'evenement, pas de temps associé
assert !this.eve.isEmpty() || this.firstTime == -1;
}
 
return true;
 
}
243,22 → 529,22
 
private void reset() {
this.value = "";
this.valueCode.clear();
this.lastPressedkeyCode = 0;
this.eve.clear();
this.firstTime = -1;
}
 
public Map<Integer, String> getMapCharacterFR() {
return this.mapCharacterFR;
}
 
public void setDebug(boolean debug) {
this.debug = debug;
}
 
public static void main(String[] args) {
String delay = "80";
final String delay;
if (args.length > 0) {
delay = args[0];
} else {
delay = "40";
}
final int d = Integer.parseInt(delay);
SwingUtilities.invokeLater(new Runnable() {
270,32 → 556,170
} catch (Exception e) {
e.printStackTrace();
}
BarcodeReader reader = new BarcodeReader(d);
System.out.println("BarCode reader");
System.out.println("Using inter key delay: " + d);
JFrame f = new JFrame();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel panel = new JPanel();
f.setTitle("Barcode reader test");
final JPanel panel = new JPanel();
f.setTitle("Barcode reader tester (AIM ID required for GS1)");
f.setContentPane(panel);
panel.setLayout(new GridBagLayout());
GridBagConstraints c = new DefaultGridBagConstraints();
GridBagConstraints c = new GridBagConstraints();
 
c.gridx = 0;
c.gridy = 0;
c.weighty = 0.5;
c.fill = GridBagConstraints.BOTH;
final KeyEventTableModel keyEventTableModel = reader.new KeyEventTableModel();
JTable table = new JTable(keyEventTableModel);
SimpleDateFormat df = new SimpleDateFormat(" hh:mm:ss.SSS");
table.getColumnModel().getColumn(0).setCellRenderer(new DefaultTableCellRenderer() {
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
Date d = (Date) value;
value = df.format(d);
if (table.getModel().getRowCount() > 0) {
Date d1 = (Date) table.getModel().getValueAt(0, 0);
value += " " + (d.getTime() - d1.getTime()) + " ms";
}
return super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
}
});
 
table.getColumnModel().getColumn(3).setCellRenderer(new DefaultTableCellRenderer() {
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
 
Component c = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
 
String str = (String) value;
if (str.equals(KeyEventTableModel.CHAR_UNDEFINED)) {
 
String id = table.getModel().getValueAt(row, 0).toString();
if (id.equals(KeyEventTableModel.KEY_TYPED)) {
c.setBackground(Color.YELLOW);
}
}
return c;
 
}
});
 
panel.add(new JScrollPane(table), c);
final JLabel l = new JLabel("BarCode reader output :");
panel.add(l, c);
c.gridy++;
c.weighty = 1;
c.weightx = 1;
c.fill = GridBagConstraints.BOTH;
final ITextArea t1 = new ITextArea();
 
final JTextArea t1 = new JTextArea(20, 10);
t1.setLineWrap(true);
t1.setWrapStyleWord(true);
t1.setMinimumSize(new Dimension(t1.getMinimumSize()));
 
panel.add(new JScrollPane(t1), c);
 
BarcodeReader reader = new BarcodeReader(d);
JPanel tools = new JPanel();
tools.setLayout(new FlowLayout(FlowLayout.RIGHT));
 
JSpinner spin = new JSpinner(new SpinnerNumberModel(d, 5, 800, 10));
spin.addChangeListener(new ChangeListener() {
 
@Override
public void stateChanged(ChangeEvent e) {
int v = ((Number) spin.getValue()).intValue();
reader.setMaxInterKeyDelay(v);
}
});
tools.add(spin);
JButton b = new JButton("Reset");
tools.add(b);
JButton bExport = new JButton("Export");
tools.add(bExport);
c.weighty = 0;
c.gridx = 0;
c.gridy++;
c.gridwidth = 2;
 
panel.add(tools, c);
 
reader.setDebug(true);
bExport.addActionListener(new ActionListener() {
 
System.err.println("FR MAP");
for (Entry<Integer, String> string : reader.getMapCharacterFR().entrySet()) {
System.err.println(string.getKey() + " --> " + string.getValue());
@Override
public void actionPerformed(ActionEvent e) {
int colCount = keyEventTableModel.getColumnCount();
int rowCount = keyEventTableModel.getRowCount();
StringBuilder b = new StringBuilder();
SimpleDateFormat df = new SimpleDateFormat("hh:mm:ss.SSS");
for (int i = 0; i < rowCount; i++) {
for (int j = 0; j < colCount; j++) {
Object o = keyEventTableModel.getValueAt(i, j);
if (o instanceof Date) {
b.append(df.format((Date) o));
} else {
final String string = o.toString();
if (string.equals("\n")) {
b.append("\\n");
} else if (string.equals("\r")) {
b.append("\\r");
} else {
b.append(string);
}
}
b.append(';');
}
b.append("\n");
}
 
JFileChooser fileChooser = new JFileChooser();
fileChooser.setSelectedFile(new File("OpenConcerto-KeyEvents.txt"));
int retval = fileChooser.showSaveDialog(panel);
if (retval == JFileChooser.APPROVE_OPTION) {
File file = fileChooser.getSelectedFile();
if (file == null) {
return;
}
if (!file.getName().toLowerCase().endsWith(".txt")) {
file = new File(file.getParentFile(), file.getName() + ".txt");
}
try (OutputStreamWriter out = new OutputStreamWriter(new FileOutputStream(file), "utf-8")) {
out.write(b.toString());
out.write(t1.getText());
out.write("\n");
out.write("Delay: " + delay);
out.flush();
} catch (Exception ex) {
ex.printStackTrace();
}
if (file.exists()) {
try {
Desktop.getDesktop().open(file);
} catch (IOException e1) {
e1.printStackTrace();
}
}
}
}
});
b.addActionListener(new ActionListener() {
 
@Override
public void actionPerformed(ActionEvent e) {
t1.setText("");
keyEventTableModel.clear();
 
}
});
reader.addKeyEventDispatcher(new KeyEventDispatcher() {
 
@Override
public boolean dispatchKeyEvent(KeyEvent e) {
keyEventTableModel.add(e);
return false;
}
});
reader.addBarcodeListener(new BarcodeListener() {
 
@Override
304,25 → 728,32
}
 
@Override
public void barcodeRead(String code) {
t1.append("Barcode OK : '" + code + "'\n");
t1.append("Hex: " + StringUtils.bytesToHexString(code.getBytes()));
t1.append("\n");
public void barcodeRead(Barcode code) {
t1.append("Barcode OK : '" + code.getCode() + "'\nType : " + code.getType() + " \n");
t1.append("Hex: " + bytesToHexString(code.getCode().getBytes()) + "'\n");
t1.append("Data : '" + code.getData() + "'\n");
 
GS1Util e = new GS1Util();
try {
t1.append("GS1: " + e.parseFromScanner(code).formatHumanReadable());
t1.append("GS1 : " + e.parse(code).formatHumanReadable());
} catch (Exception ex) {
t1.append("GS1: " + ex.getMessage());
final String message = ex.getMessage();
if (message == null) {
t1.append("Not a GS1 code");
} else
t1.append("Not a GS1 code : " + message);
}
t1.append("\n\n");
}
});
 
f.setSize(new Dimension(640, 480));
t1.setEditable(false);
f.setSize(new Dimension(640, 580));
f.setLocationRelativeTo(null);
f.setVisible(true);
 
}
 
});
 
}
330,4 → 761,25
public void setEnabled(boolean b) {
this.enable = b;
}
 
static final char[] hexArray = "0123456789ABCDEF".toCharArray();
 
public static String charToHex(char c) {
int v = c & 0xFF;
char[] hexChars = new char[2];
hexChars[0] = hexArray[v >>> 4];
hexChars[1] = hexArray[v & 0x0F];
return new String(hexChars);
}
 
public static String bytesToHexString(byte[] bytes) {
int length = bytes.length;
char[] hexChars = new char[length * 2];
for (int j = 0; j < length; j++) {
int v = bytes[j] & 0xFF;
hexChars[j * 2] = hexArray[v >>> 4];
hexChars[j * 2 + 1] = hexArray[v & 0x0F];
}
return new String(hexChars);
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/io/BarcodeListener.java
New file
0,0 → 1,23
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
* copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each file.
*/
package org.openconcerto.erp.core.sales.pos.io;
 
import java.awt.event.KeyEvent;
 
public interface BarcodeListener {
 
void barcodeRead(Barcode code);
 
void keyReceived(KeyEvent ee);
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/sales/pos/element/TicketCaisseSQLElement.java
13,16 → 13,17
package org.openconcerto.erp.core.sales.pos.element;
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.finance.payment.element.TypeReglementSQLElement;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.pos.TicketSheetXML;
import org.openconcerto.erp.core.sales.pos.POSConfiguration;
import org.openconcerto.erp.core.sales.pos.model.Article;
import org.openconcerto.erp.core.sales.pos.model.ArticleCache;
import org.openconcerto.erp.core.sales.pos.model.Categorie;
import org.openconcerto.erp.core.sales.pos.model.Paiement;
import org.openconcerto.erp.core.sales.pos.model.ReceiptCode;
import org.openconcerto.erp.core.sales.pos.model.Ticket;
import org.openconcerto.erp.core.sales.pos.ui.TicketClientNamePanel;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLComponent;
import org.openconcerto.sql.element.SQLElement;
35,6 → 36,7
import org.openconcerto.sql.utils.PartialUniqueTrigger;
import org.openconcerto.sql.view.list.IListeAction.IListeEvent;
import org.openconcerto.sql.view.list.action.SQLRowValuesAction.PredicateRowAction;
import org.openconcerto.ui.FrameUtil;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
 
42,11 → 44,11
import java.text.ParseException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
 
import javax.swing.JFrame;
import javax.swing.JTextField;
 
public class TicketCaisseSQLElement extends ComptaSQLConfElement {
72,13 → 74,21
super("TICKET_CAISSE", "un ticket de caisse", "tickets de caisses");
 
PredicateRowAction action = new PredicateRowAction(true, "ticket.document.generate", (le) -> {
final TicketSheetXML bSheet = new TicketSheetXML(createTicket(le.getSelectedRow().asRow()), ComptaPropsConfiguration.getInstanceCompta());
 
POSConfiguration posConf = POSConfiguration.getInstance();
try {
bSheet.createDocument();
bSheet.showPrintAndExport(true, false, false, Collections.emptyList());
} catch (Exception originalExn) {
ExceptionHandler.handle("Erreur lors de la création de la facture", originalExn);
if (posConf == null) {
posConf = POSConfiguration.setInstance();
ArticleCache.initCache(getDirectory());
}
} catch (Exception e) {
ExceptionHandler.handle("Impossible d'initialiser la configuration de la caisse", e);
return;
}
TicketClientNamePanel p = new TicketClientNamePanel(null, createTicket(le.getSelectedRow().asRow()));
JFrame f = new JFrame("Facturation ticket");
f.add(p);
FrameUtil.showPacked(f);
});
 
action.setPredicate(IListeEvent.getSingleSelectionPredicate());
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/element/SocieteCommonSQLElement.java
242,7 → 242,7
 
c.gridx++;
c.weightx = 1;
final SQLRequestComboBox comboIDCC = new SQLRequestComboBox();
final ElementComboBox comboIDCC = new ElementComboBox();
this.add(comboIDCC, c);
this.addView(comboIDCC, "ID_IDCC");
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/element/ComptaSQLConfElement.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
15,9 → 15,20
 
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.model.DBRoot;
import org.openconcerto.sql.model.SQLField;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.request.ComboSQLRequest;
import org.openconcerto.sql.users.UserManager;
import org.openconcerto.sql.users.rights.UserRights;
import org.openconcerto.sql.users.rights.UserRightsManager;
import org.openconcerto.sql.view.list.SQLTableModelSource;
import org.openconcerto.task.config.ComptaBasePropsConfiguration;
 
import java.util.List;
 
/**
* SQLElement de la base société
*
28,6 → 39,10
 
private static DBRoot baseSociete;
 
// Attention limité la modification de table commercial à l'admin pour que le user ne puisse pas
// réaffecter les liens commercial<->user
public static String NON_RESTREINT_PAR_COMMERCIAL_RIGHT = "NON_RESTREINT_PAR_COMMERCIAL";
 
private static DBRoot getBaseSociete() {
if (baseSociete == null)
baseSociete = ((ComptaBasePropsConfiguration) Configuration.getInstance()).getRootSociete();
62,4 → 77,44
super(table, code);
}
 
public void addCommercialFilter(final SQLTableModelSource source, final SQLField fieldCommercial) {
final UserRights rights = UserRightsManager.getCurrentUserRights();
if (!rights.haveRight(NON_RESTREINT_PAR_COMMERCIAL_RIGHT)) {
source.getReq().putWhere(NON_RESTREINT_PAR_COMMERCIAL_RIGHT, getWhereCommercial(fieldCommercial));
}
}
 
private Where getWhereCommercial(final SQLField fieldCommercial) {
SQLRow row = fieldCommercial.getTable().getDBRoot().findTable("USER_COMMON").getRow(UserManager.getInstance().getCurrentUser().getId());
List<SQLRow> rows = row.getReferentRows(fieldCommercial.getForeignTable().getField("ID_USER_COMMON"));
 
Where w = null;
 
if (rows.isEmpty()) {
w = Where.FALSE;
} else {
for (SQLRow sqlRow : rows) {
if (fieldCommercial.getTable().getName().equals(getTable().getName())) {
w = Where.or(w, new Where(fieldCommercial, "=", sqlRow.getID()));
} else {
// CLIENT.ID_COMMERCIAL in CONTACT
SQLField field = getTable().getField("ID_" + fieldCommercial.getTable().getName());
SQLSelect selIDClient = new SQLSelect();
selIDClient.addSelect(fieldCommercial.getTable().getKey());
selIDClient.setWhere(new Where(fieldCommercial, "=", sqlRow.getID()));
 
Where wClient = Where.createRaw(field.getSQLName().quote() + " IN (" + selIDClient.asString() + ")", field);
w = Where.or(w, wClient);
}
}
}
return w;
}
 
public void addCommercialFilterCombo(final ComboSQLRequest req, final SQLField fieldCommercial) {
final UserRights rights = UserRightsManager.getCurrentUserRights();
if (!rights.haveRight(NON_RESTREINT_PAR_COMMERCIAL_RIGHT)) {
req.putWhere(NON_RESTREINT_PAR_COMMERCIAL_RIGHT, getWhereCommercial(fieldCommercial));
}
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/element/NumerotationAutoSQLElement.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
574,7 → 574,11
public static void fixNumerotation(SQLElement elt) {
 
SQLRow rowNum = TABLE_NUM.getRow(2);
String s = map.get(elt.getClass());
 
for (Class<? extends SQLElement> itemToFix : map.keySet()) {
if (itemToFix.isAssignableFrom(elt.getClass())) {
String s = map.get(itemToFix);
 
if (!rowNum.getTable().contains(s + AUTO_MONTH) || !rowNum.getBoolean(s + AUTO_MONTH)) {
 
if (rowNum.getObject(s + START) != null) {
582,11 → 586,11
int start = rowNum.getInt(s + START);
 
// si le numero precedent n'existe pas
if (!isNumeroExist(elt, start - 1)) {
if (!isNumeroExist(elt.getDirectory().getElement(itemToFix), start - 1)) {
 
int i = 2;
 
while (!isNumeroExist(elt, start - i)) {
while (!isNumeroExist(elt.getDirectory().getElement(itemToFix), start - i)) {
i++;
}
 
603,6 → 607,8
}
}
}
}
}
 
private static Map<Class<? extends SQLElement>, String> map = new HashMap<Class<? extends SQLElement>, String>();
 
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/ItemAutoCompletionManager.java
18,6 → 18,7
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.request.ComboSQLRequest;
import org.openconcerto.sql.view.list.AutoCompletionManager;
import org.openconcerto.sql.view.list.RowValuesTable;
import org.openconcerto.sql.view.list.RowValuesTableModel;
36,6 → 37,12
this.t = t;
}
 
public ItemAutoCompletionManager(AbstractVenteArticleItemTable t, SQLTableElement tableElementCode, SQLField field, RowValuesTable table, RowValuesTableModel rowValuesTableModel,
ComboSQLRequest req) {
super(tableElementCode, field, table, rowValuesTableModel, req);
this.t = t;
}
 
public ItemAutoCompletionManager(AbstractVenteArticleItemTable t, SQLTableElement tableElementArticle, SQLField field, RowValuesTable table, RowValuesTableModel rowValuesTableModel,
int modeContains, boolean b, boolean c, ValidStateChecker validStateChecker) {
super(tableElementArticle, field, table, rowValuesTableModel, modeContains, b, c, validStateChecker);
57,6 → 64,9
} else {
if (piece && toField.equals("QTE_UNITAIRE")) {
to.put(toField, BigDecimal.ONE);
// On ne remet la quantité par défaut que si la quantité est égale à 1 pour ne
// pas écraser une valeur déjà saisie
if (to.getObject("QTE") == null || to.getInt("QTE") == 1) {
// Pour les pièces commercials de vente
to.put("QTE", from.getBigDecimal("QTE_UNITAIRE").setScale(0, RoundingMode.HALF_UP).intValue());
// Pour les bons de livraison
63,7 → 73,14
if (to.getTable().getName().equals("BON_DE_LIVRAISON_ELEMENT")) {
to.put("QTE_A_LIVRER", from.getBigDecimal("QTE_UNITAIRE").setScale(0, RoundingMode.HALF_UP).intValue());
}
}
} else if (toField.equals("QTE_UNITAIRE")) {
if (to.getObject("QTE_UNITAIRE") == null || to.getBigDecimal("QTE_UNITAIRE").equals(BigDecimal.ONE)) {
to.put(toField, valueFrom);
}
 
} else {
 
to.put(toField, valueFrom);
}
}
81,8 → 98,12
boolean piece = from.getForeignID("ID_UNITE_VENTE") == UniteVenteArticleSQLElement.A_LA_PIECE;
if (piece) {
if (field.equals("QTE")) {
if (rowDest.getObject("QTE") == null || rowDest.getInt("QTE") == 1) {
return from.getBigDecimal("QTE_UNITAIRE").setScale(0, RoundingMode.HALF_UP).intValue();
} else {
return rowDest.getObject("QTE");
}
}
if (field.equals("QTE_UNITAIRE")) {
return BigDecimal.ONE;
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/DeviseField.java
1,7 → 1,7
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 2011 OpenConcerto, by ILM Informatique. All rights reserved.
* Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
*
* The contents of this file are subject to the terms of the GNU General Public License Version 3
* only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
273,4 → 273,11
public boolean isDocTransversable() {
return false;
}
 
@Override
public void setText(String t) {
if (!this.getText().equals(t)) {
super.setText(t);
}
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/TotalCalculator.java
532,7 → 532,6
if (!this.achat) {
// Total Service
if (this.bServiceActive != null && this.bServiceActive && service != null && service.booleanValue()) {
this.totalService = this.totalService.add(totalLineHT);
cpt = this.rowDefaultCptService;
if (tva != null && !tva.isForeignEmpty("ID_COMPTE_PCE_VENTE_SERVICE")) {
cpt = cacheForTableCompte.getRowFromId(tva.getForeignID("ID_COMPTE_PCE_VENTE_SERVICE"));
685,6 → 684,8
* Vérifie si ht + tva = ttc
*/
public void checkResult() {
// Total global
{
BigDecimal ht = getTotalHT();
BigDecimal tva = getTotalTVA();
BigDecimal totalTTC2 = getTotalTTC();
709,6 → 710,23
}
}
}
// Selection
{
BigDecimal ht = getTotalHTSel();
BigDecimal tva = getTotalTVASel();
BigDecimal totalTTC2 = getTotalTTCSel();
BigDecimal reste = totalTTC2.subtract(ht.add(tva));
if (!this.intraComm && reste.compareTo(BigDecimal.ZERO) != 0) {
for (SQLRowAccessor rHT : this.mapHtSel.keySet()) {
BigDecimal input = this.mapHtSel.get(rHT);
if (input != null && input.signum() != 0) {
this.mapHtSel.put(rHT, input.add(reste));
break;
}
}
}
}
}
 
public BigDecimal getTotalDevise() {
return this.totalDevise;
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/AbstractArticleItemTable.java
13,15 → 13,22
package org.openconcerto.erp.core.common.ui;
 
import org.openconcerto.erp.config.ComptaPropsConfiguration;
import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.common.element.StyleSQLElement;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.product.component.BatchSelectorFrame;
import org.openconcerto.erp.core.sales.product.element.LotReceptionSQLElement;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.erp.core.sales.product.element.UniteVenteArticleSQLElement;
import org.openconcerto.erp.core.sales.product.model.BatchQuantity;
import org.openconcerto.erp.core.supplychain.receipt.ui.LotReceptionUIPanel;
import org.openconcerto.erp.preferences.DefaultNXProps;
import org.openconcerto.erp.preferences.GestionArticleGlobalPreferencePanel;
import org.openconcerto.erp.utils.TM;
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.element.SQLElementDirectory;
import org.openconcerto.sql.model.SQLField;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
43,13 → 50,18
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.File;
import java.math.BigDecimal;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
56,10 → 68,14
 
import javax.swing.AbstractAction;
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.ScrollPaneConstants;
import javax.swing.SwingUtilities;
import javax.swing.table.TableCellEditor;
 
public abstract class AbstractArticleItemTable extends JPanel {
protected RowValuesTable table;
145,6 → 161,140
c.weightx = 1;
 
this.buttons.add(1, new AjoutDeclinaisonButton(this));
if (getSQLElement().getTable().getName().equals("BON_RECEPTION_ELEMENT")) {
this.buttons.add(1, new JButton(new AbstractAction("Lot / N° série") {
 
@Override
public void actionPerformed(ActionEvent e) {
final JFrame root = (JFrame) SwingUtilities.getRoot(AbstractArticleItemTable.this);
final int selectedRow = getRowValuesTable().getSelectedRow();
if (selectedRow == -1) {
JOptionPane.showMessageDialog(root, "Aucune ligne sélectionnée!");
} else {
final SQLRowValues rowValuesAt = getRowValuesTable().getRowValuesTableModel().getRowValuesAt(selectedRow);
if (rowValuesAt.isForeignEmpty("ID_ARTICLE")) {
JOptionPane.showMessageDialog(root, "Aucun article sur ligne sélectionnée!");
} else {
final Number foreignIDNumberUnite = rowValuesAt.getForeignIDNumber("ID_UNITE_VENTE");
 
JDialog d = new JDialog(root, "Lot / N° série", true);
final LotReceptionSQLElement elementLotR = getSQLElement().getDirectory().getElement(LotReceptionSQLElement.class);
d.getContentPane().add(new LotReceptionUIPanel(elementLotR, rowValuesAt));
d.pack();
d.setLocationRelativeTo(null);
d.setVisible(true);
d.addWindowListener(new WindowAdapter() {
 
@Override
public void windowClosed(WindowEvent e) {
final TableCellEditor cellEditor = getRowValuesTable().getCellEditor();
if (cellEditor != null) {
cellEditor.stopCellEditing();
}
final Set<SQLRowValues> referentRows = rowValuesAt.getReferentRows(elementLotR.getTable().getField("ID_BON_RECEPTION_ELEMENT"));
BigDecimal b = BigDecimal.ZERO;
for (SQLRowValues sqlRowValues : referentRows) {
if (!sqlRowValues.contains("ARCHIVE") || !sqlRowValues.isArchived()) {
b = b.add(sqlRowValues.getBigDecimal("QUANTITE"));
}
}
if (b.signum() != 0) {
if (foreignIDNumberUnite != null && foreignIDNumberUnite.intValue() == UniteVenteArticleSQLElement.A_LA_PIECE) {
getRowValuesTable().getRowValuesTableModel().setValueAt(b.intValue(), selectedRow, getRowValuesTable().getRowValuesTableModel().getColumnForField("QTE"));
} else {
getRowValuesTable().getRowValuesTableModel().setValueAt(1, selectedRow, getRowValuesTable().getRowValuesTableModel().getColumnForField("QTE"));
getRowValuesTable().getRowValuesTableModel().setValueAt(b, selectedRow, getRowValuesTable().getRowValuesTableModel().getColumnForField("QTE_UNITAIRE"));
}
}
}
 
});
}
}
}
}));
} else if (getSQLElement().getTable().getName().equals("BON_DE_LIVRAISON_ELEMENT")) {
this.buttons.add(1, new JButton(new AbstractAction("Lot / N° série") {
private final Map<SQLRowValues, BigDecimal> mapDBQuantity = new HashMap<>();
 
@Override
public void actionPerformed(ActionEvent e) {
final JFrame root = (JFrame) SwingUtilities.getRoot(AbstractArticleItemTable.this);
final int selectedRow = getRowValuesTable().getSelectedRow();
if (selectedRow == -1) {
JOptionPane.showMessageDialog(root, "Aucune ligne sélectionnée!");
} else {
final SQLRowValues rowValuesAt = getRowValuesTable().getRowValuesTableModel().getRowValuesAt(selectedRow);
if (rowValuesAt.isForeignEmpty("ID_ARTICLE")) {
JOptionPane.showMessageDialog(root, "Aucun article sur ligne sélectionnée!");
} else {
final Number foreignIDNumberUnite = rowValuesAt.getForeignIDNumber("ID_UNITE_VENTE");
 
final SQLElementDirectory directory = getSQLElement().getDirectory();
final Set<SQLRowValues> referentRows = rowValuesAt.getReferentRows(getSQLElement().getTable().getTable("LOT_LIVRAISON").getField("ID_BON_DE_LIVRAISON_ELEMENT"));
try {
 
List<SQLRowValues> listRefRows = new ArrayList<SQLRowValues>();
for (SQLRowValues sqlRowValues : referentRows) {
if (!mapDBQuantity.containsKey(sqlRowValues)) {
mapDBQuantity.put(sqlRowValues, sqlRowValues.getBigDecimal("QUANTITE"));
}
if (!sqlRowValues.contains("ARCHIVE") || !sqlRowValues.isArchived()) {
listRefRows.add(sqlRowValues);
}
}
 
final List<BatchQuantity> createBatchQuantity = directory.getElement(LotSQLElement.class).createBatchQuantity(listRefRows);
for (int i = 0; i < createBatchQuantity.size(); i++) {
final SQLRowValues ref = listRefRows.get(i);
if (mapDBQuantity.containsKey(ref)) {
createBatchQuantity.get(i).setQuantityInDB(mapDBQuantity.get(ref));
}
}
 
final BatchSelectorFrame frame = new BatchSelectorFrame(root, directory, rowValuesAt.getForeign("ID_ARTICLE").asRow(), createBatchQuantity);
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
 
frame.pack();
frame.setVisible(true);
frame.setLocationRelativeTo(null);
frame.addWindowListener(new WindowAdapter() {
 
@Override
public void windowClosed(WindowEvent e) {
 
if (frame.isCancelled())
return;
 
final TableCellEditor cellEditor = getRowValuesTable().getCellEditor();
if (cellEditor != null) {
cellEditor.stopCellEditing();
}
 
final List<BatchQuantity> quantities = frame.getQuantities();
directory.getElement(LotSQLElement.class).createLotLivraison(quantities, rowValuesAt);
 
BigDecimal b = frame.getTotalSelectedQuantity();
if (b.signum() != 0) {
if (foreignIDNumberUnite != null && foreignIDNumberUnite.intValue() == UniteVenteArticleSQLElement.A_LA_PIECE) {
getRowValuesTable().getRowValuesTableModel().setValueAt(b.intValue(), selectedRow,
getRowValuesTable().getRowValuesTableModel().getColumnForField("QTE_LIVREE"));
} else {
getRowValuesTable().getRowValuesTableModel().setValueAt(1, selectedRow, getRowValuesTable().getRowValuesTableModel().getColumnForField("QTE_LIVREE"));
getRowValuesTable().getRowValuesTableModel().setValueAt(b, selectedRow, getRowValuesTable().getRowValuesTableModel().getColumnForField("QTE_UNITAIRE"));
}
}
}
 
});
} catch (SQLException e1) {
ExceptionHandler.handle("Erreur lors de la récupération des lots", e1);
}
}
}
}
}));
}
control = new RowValuesTableControlPanel(this.table, this.buttons);
control.setOpaque(false);
this.add(control, c);
264,7 → 414,7
 
final SQLElement eltArticleTable = getSQLElement();
 
final SQLTable tableArticle = ((ComptaPropsConfiguration) Configuration.getInstance()).getRootSociete().getTable("ARTICLE");
final SQLTable tableArticle = getSQLElement().getTable().getTable("ARTICLE");
 
final boolean modeAvance = DefaultNXProps.getInstance().getBooleanValue("ArticleModeVenteAvance", false);
SQLPreferences prefs = SQLPreferences.getMemCached(tableArticle.getDBRoot());
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/AbstractAchatArticleItemTable.java
17,11 → 17,15
import org.openconcerto.erp.core.finance.accounting.model.CurrencyConverter;
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.pos.io.BarcodeReader;
import org.openconcerto.erp.core.sales.pos.ui.BarcodeListener;
import org.openconcerto.erp.core.sales.pos.io.Barcode;
import org.openconcerto.erp.core.sales.pos.io.BarcodeListener;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.erp.core.sales.product.element.UniteVenteArticleSQLElement;
import org.openconcerto.erp.core.sales.product.element.LotSQLElement.TypeLot;
import org.openconcerto.erp.core.sales.product.ui.CurrencyWithSymbolRenderer;
import org.openconcerto.erp.core.sales.product.ui.DeliveredQtyRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.QtyRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.QteMultipleRowValuesRenderer;
import org.openconcerto.erp.core.sales.product.ui.QteUnitRowValuesRenderer;
import org.openconcerto.erp.core.supplychain.stock.element.DepotStockSQLElement;
import org.openconcerto.erp.core.supplychain.stock.element.StockSQLElement;
30,10 → 34,12
import org.openconcerto.sql.Configuration;
import org.openconcerto.sql.element.SQLElement;
import org.openconcerto.sql.model.FieldPath;
import org.openconcerto.sql.model.SQLField;
import org.openconcerto.sql.model.SQLRow;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.model.SQLRowListRSH;
import org.openconcerto.sql.model.SQLRowValues;
import org.openconcerto.sql.model.SQLRowValuesListFetcher;
import org.openconcerto.sql.model.SQLSelect;
import org.openconcerto.sql.model.SQLTable;
import org.openconcerto.sql.model.UndefinedRowValuesCache;
40,6 → 46,7
import org.openconcerto.sql.model.Where;
import org.openconcerto.sql.model.graph.Path;
import org.openconcerto.sql.preferences.SQLPreferences;
import org.openconcerto.sql.request.ComboSQLRequest;
import org.openconcerto.sql.sqlobject.ITextArticleWithCompletionCellEditor;
import org.openconcerto.sql.sqlobject.ITextWithCompletion;
import org.openconcerto.sql.view.EditFrame;
51,9 → 58,11
import org.openconcerto.sql.view.list.SQLTableElement;
import org.openconcerto.sql.view.list.ValidStateChecker;
import org.openconcerto.ui.preferences.DefaultProps;
import org.openconcerto.utils.CompareUtils;
import org.openconcerto.utils.DecimalUtils;
import org.openconcerto.utils.ExceptionHandler;
import org.openconcerto.utils.Tuple3;
import org.openconcerto.utils.checks.ValidState;
import org.openconcerto.utils.i18n.TranslationManager;
 
import java.awt.Component;
66,9 → 75,11
import java.awt.event.MouseEvent;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Calendar;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
173,7 → 184,7
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
boolean b = super.isCellEditable(vals, rowIndex, columnIndex);
 
return b && !isFromTranferred(vals);
return b && !isFromTranferred(vals) && !isLotLinked(vals);
 
}
 
213,7 → 224,7
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
boolean b = super.isCellEditable(vals, rowIndex, columnIndex);
return b && !isFromTranferred(vals);
return b && !isFromTranferred(vals) && !isLotLinked(vals);
 
}
};
223,7 → 234,7
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
boolean b = super.isCellEditable(vals, rowIndex, columnIndex);
return b && !isFromTranferred(vals);
return b && !isFromTranferred(vals) && !isLotLinked(vals);
 
}
};
303,7 → 314,7
if (row != null && !row.isUndefined() && row.getBoolean("A_LA_PIECE")) {
return false;
} else {
return super.isCellEditable(vals, rowIndex, columnIndex);
return super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
}
}
 
365,13 → 376,27
}
 
// Quantité
final SQLTableElement qteElement = new SQLTableElement(e.getTable().getField("QTE"), Integer.class) {
final SQLTableElement qteElement = new SQLTableElement(e.getTable().getField("QTE"), Integer.class, new QteCellEditor()) {
protected Object getDefaultNullValue() {
return Integer.valueOf(0);
}
 
@Override
public boolean isCellEditable(SQLRowValues vals, int rowIndex, int columnIndex) {
 
return super.isCellEditable(vals, rowIndex, columnIndex) && !isLotLinked(vals);
}
 
public TableCellRenderer getTableCellRenderer() {
if (getSQLElement().getTable().getFieldsName().contains("QTE_ACHAT")) {
return new QteMultipleRowValuesRenderer();
} else {
return super.getTableCellRenderer();
}
}
};
if (fieldsName.contains("QTE_ORIGINE")) {
qteElement.setRenderer(new DeliveredQtyRowValuesRenderer(false));
qteElement.setRenderer(new QtyRowValuesRenderer(false));
}
list.add(qteElement);
// TVA
535,14 → 560,75
 
final RowValuesTableModel model = new RowValuesTableModel(e, list, e.getTable().getField("QTE"), false, this.defaultRowVals) {
@Override
public void commitData() {
super.commitData(true);
public void commitData() throws SQLException {
commitData(true);
}
 
@Override
public void commitData(boolean useMultipleInsertUpdate) throws SQLException {
if (getSQLElement().getTable().getName().equalsIgnoreCase("BON_RECEPTION_ELEMENT")) {
// Mise à jour de l'ID_ARTICLE et l'ID_DEPOT_STOCK
final SQLTable tableLotR = getSQLElement().getTable().getTable("LOT_RECEPTION");
for (int i = 0; i < getRowCount(); i++) {
final SQLRowValues rowValuesAt = getRowValuesAt(i);
final Set<SQLRowValues> referentRows = rowValuesAt.getReferentRows(tableLotR.getField("ID_BON_RECEPTION_ELEMENT"));
for (SQLRowValues ref : referentRows) {
ref.put("ID_ARTICLE", rowValuesAt.getForeignIDNumber("ID_ARTICLE"));
ref.put("ID_DEPOT_STOCK", rowValuesAt.getForeignIDNumber("ID_DEPOT_STOCK"));
}
}
}
super.commitData(useMultipleInsertUpdate);
if (getSQLElement().getTable().getName().equalsIgnoreCase("BON_RECEPTION_ELEMENT")) {
getSQLElement().getDirectory().getElement(LotSQLElement.class).updateLotQuantiteFromBRItems(getCopyOfValues());
}
}
 
@Override
public List<SQLRowValues> fetchDataFromDB(SQLRowAccessor rowVals, SQLField referentField, SQLField fieldWhere, Object value) {
final SQLTable table = getSQLElement().getTable();
List<SQLRowValues> newRows = new ArrayList<>();
SQLRowValues rowValsBrItem = new SQLRowValues(table);
rowValsBrItem.putNulls(table.getFieldsName());
rowValsBrItem.putRowValues("ID_UNITE_VENTE").putNulls("A_LA_PIECE");
rowValsBrItem.putRowValues("ID_ARTICLE").putNulls("CODE", "NOM", "DLC_REQUIS", "DLUO_REQUIS", "NUMERO_LOT_REQUIS", "NUMERO_SERIE_REQUIS");
if (table.getName().equals("BON_RECEPTION_ELEMENT")) {
final SQLTable tableLotR = table.getTable("LOT_RECEPTION");
SQLRowValues rowValsLotRecp = new SQLRowValues(tableLotR);
rowValsLotRecp.putNulls(rowValsLotRecp.getTable().getFieldsName());
rowValsLotRecp.put("ID_BON_RECEPTION_ELEMENT", rowValsBrItem);
}
if (referentField == null) {
referentField = table.getField("ID_" + rowVals.getTable().getName());
}
final List<SQLRowValues> fetch = SQLRowValuesListFetcher.create(rowValsBrItem).fetch(new Where(referentField, "=", rowVals.getID()));
for (SQLRowValues row2 : fetch) {
if (fieldWhere == null || CompareUtils.equals(row2.getObject(fieldWhere.getName()), value)) {
newRows.add(row2);
}
}
return newRows;
}
 
};
 
if (getSQLElement().getTable().getName().equalsIgnoreCase("BON_RECEPTION_ELEMENT")) {
model.setGestionReferentActive(true);
}
setModel(model);
 
this.table = new RowValuesTable(model, getConfigurationFile());
this.table = new RowValuesTable(model, getConfigurationFile()) {
@Override
public synchronized ValidState getValidState() {
if (getSQLElement().getTable().getName().equalsIgnoreCase("BON_RECEPTION_ELEMENT")) {
final LotSQLElement element = getSQLElement().getDirectory().getElement(LotSQLElement.class);
ValidState lotState = element.getValidStateOfRowValuesTable(getRowValuesTable().getRowValuesTableModel(), TypeLot.RECEPTION);
if (lotState != ValidState.getTrueInstance()) {
return lotState;
}
}
return super.getValidState();
}
};
ToolTipManager.sharedInstance().unregisterComponent(this.table);
ToolTipManager.sharedInstance().unregisterComponent(this.table.getTableHeader());
if (getSQLElement().getTable().getName().equals("COMMANDE_ELEMENT")) {
628,6 → 714,7
completionFields.add("PV_HT");
completionFields.add("POIDS");
completionFields.add("ID_TAXE");
completionFields.add("ID_MODE_VENTE_ARTICLE");
completionFields.add("PRIX_METRIQUE_HA_1");
completionFields.add("PRIX_METRIQUE_HA_2");
completionFields.add("PRIX_METRIQUE_HA_3");
634,7 → 721,6
completionFields.add("VALEUR_METRIQUE_1");
completionFields.add("VALEUR_METRIQUE_2");
completionFields.add("VALEUR_METRIQUE_3");
completionFields.add("ID_MODE_VENTE_ARTICLE");
completionFields.add("PRIX_METRIQUE_VT_1");
completionFields.add("PRIX_METRIQUE_VT_2");
completionFields.add("PRIX_METRIQUE_VT_3");
659,6 → 745,9
if (getSQLElement().getTable().getFieldsName().contains("TARE") && sqlTableArticle.getTable().getFieldsName().contains("TARE")) {
completionFields.add("TARE");
}
if (getSQLElement().getTable().getFieldsName().contains("QTE_ACHAT") && sqlTableArticle.getTable().getFieldsName().contains("QTE_ACHAT")) {
completionFields.add("QTE_ACHAT");
}
this.m = new AutoCompletionManager(tableElementCode, sqlTableArticle.getField("CODE"), this.table, this.table.getRowValuesTableModel()) {
@Override
protected Object getValueFrom(SQLRow row, String field, SQLRowAccessor rowDest) {
685,8 → 774,10
final Where w = new Where(sqlTableArticle.getField("OBSOLETE"), "=", Boolean.FALSE);
m.setWhere(w);
 
ComboSQLRequest req = new ComboSQLRequest(sqlTableArticle, Arrays.asList("NOM", "CODE"));
req.setWhere(w);
this.m2 = new AutoCompletionManager(tableElementNom, ((ComptaPropsConfiguration) Configuration.getInstance()).getSQLBaseSociete().getField("ARTICLE.NOM"), this.table,
this.table.getRowValuesTableModel()) {
this.table.getRowValuesTableModel(), req) {
@Override
protected Object getValueFrom(SQLRow row, String field, SQLRowAccessor rowDest) {
Object res = tarifCompletion(row, field);
697,6 → 788,7
}
}
};
m2.setFillWithField("NOM");
m2.fill("CODE", "CODE");
m2.fill("ID", "ID_ARTICLE");
for (String string : completionFields) {
751,7 → 843,7
try {
SQLRowAccessor foreign = row.getForeign("ID_ARTICLE");
if (foreign != null && !foreign.isUndefined() && foreign.getObject("CODE") != null && foreign.getString("CODE").equals(row.getString("CODE"))) {
return foreign.getID();
return foreign/* .getID() */;
} else {
return tableArticle.getUndefinedID();
}
1046,13 → 1138,13
}
 
@Override
public void barcodeRead(String code) {
public void barcodeRead(Barcode barcode) {
if (((JFrame) SwingUtilities.getRoot(getRowValuesTable())).isActive()) {
final SQLSelect selArticle = new SQLSelect();
final SQLTable tableArticle = getSQLElement().getForeignElement("ID_ARTICLE").getTable();
selArticle.addSelectStar(tableArticle);
Where w = new Where(tableArticle.getField("OBSOLETE"), "=", Boolean.FALSE);
w = w.and(new Where(tableArticle.getField("CODE_BARRE"), "=", code));
w = w.and(new Where(tableArticle.getField("CODE_BARRE"), "=", barcode.getData()));
selArticle.setWhere(w);
List<SQLRow> l2 = SQLRowListRSH.execute(selArticle);
if (l2.size() > 0) {
1187,7 → 1279,23
} else {
incoTerms = Arrays.asList("PRIX_ACHAT");
}
List<SQLRow> rows = row.getReferentRows(tTarifFournisseur);
List<SQLRowValues> rows;
 
if (this.rowFournisseur != null && !this.rowFournisseur.isUndefined()) {
 
SQLRowValues rowValsTarif = new SQLRowValues(tTarifFournisseur);
rowValsTarif.putNulls(tTarifFournisseur.getFieldsName());
Where where = new Where(tTarifFournisseur.getField("ID_FOURNISSEUR"), "=", this.rowFournisseur.getID()).and(new Where(tTarifFournisseur.getField("ID_ARTICLE"), "=", row.getID()));
rows = SQLRowValuesListFetcher.create(rowValsTarif).fetch(where);
 
if (rows.isEmpty() && row.getObject("ID_ARTICLE_VIRTUEL_PERE") != null && !row.isForeignEmpty("ID_ARTICLE_VIRTUEL_PERE")) {
Where where2 = new Where(tTarifFournisseur.getField("ID_FOURNISSEUR"), "=", this.rowFournisseur.getID())
.and(new Where(tTarifFournisseur.getField("ID_ARTICLE"), "=", row.getForeignID("ID_ARTICLE_VIRTUEL_PERE")));
rows = SQLRowValuesListFetcher.create(rowValsTarif).fetch(where2);
}
} else {
rows = Collections.emptyList();
}
if (row.getBoolean("AUTO_PRIX_ACHAT_NOMENCLATURE") && row.getTable().getDBRoot().contains("ARTICLE_PRIX_REVIENT")) {
 
List<SQLRow> rowsElt = row.getReferentRows(row.getTable().getTable("ARTICLE_ELEMENT").getField("ID_ARTICLE_PARENT"));
1252,7 → 1360,7
BigDecimal min = row.getBigDecimal("PRIX_METRIQUE_HA_1");
 
Calendar c = null;
for (SQLRow sqlRow : rows) {
for (SQLRowValues sqlRow : rows) {
if (this.rowFournisseur != null && this.rowFournisseur.getID() == sqlRow.getForeignID("ID_FOURNISSEUR")) {
BigDecimal price = getPrice(sqlRow, incoTerms);
final Calendar datePrice = sqlRow.getDate("DATE_PRIX");
1480,4 → 1588,11
return false;
}
 
private boolean isLotLinked(SQLRowValues vals) {
if (vals.getTable().getName().equals("BON_RECEPTION_ELEMENT")) {
return !vals.getReferentRows(vals.getTable().getTable("LOT_RECEPTION").getField("ID_BON_RECEPTION_ELEMENT")).isEmpty();
}
return false;
}
 
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/IListTotalPanel.java
15,8 → 15,10
 
import org.openconcerto.erp.core.finance.accounting.model.Currency;
import org.openconcerto.erp.core.finance.accounting.model.CurrencyConverter;
import org.openconcerto.sql.model.FieldPath;
import org.openconcerto.sql.model.SQLField;
import org.openconcerto.sql.model.SQLRowAccessor;
import org.openconcerto.sql.view.list.BaseSQLTableModelColumn;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.ITableModel;
import org.openconcerto.sql.view.list.ListSQLLine;
25,6 → 27,7
import org.openconcerto.ui.JLabelBold;
import org.openconcerto.utils.TableSorter;
import org.openconcerto.utils.Tuple2;
import org.openconcerto.utils.Tuple3;
 
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
36,10 → 39,13
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ExecutionException;
 
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
import javax.swing.SwingWorker;
import javax.swing.event.EventListenerList;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
65,7 → 71,10
// Requiert le field TTC
AVANCEMENT_TTC,
// TOTAL DES LIGNES
COUNT;
COUNT,
 
// DIfference entre parama 1 et 2
DIFF;
};
 
DecimalFormat decimalFormat = new DecimalFormat("##,##0.00");
111,6 → 120,8
* @param listField Liste des fields à totaliser
* @param filters filtre ex : Tuple((SQLField)NATEXIER,(Boolean)FALSE)
*/
final GridBagConstraints c = new DefaultGridBagConstraints();
 
public IListTotalPanel(IListe l, final List<Tuple2<? extends SQLTableModelColumn, Type>> listField, final List<Tuple2<SQLField, ?>> filters, final List<Tuple2<SQLField, ?>> filtersNot,
String title, boolean onSelection) {
super(new GridBagLayout());
117,7 → 128,6
this.list = l;
this.setOpaque(false);
this.onSelection = onSelection;
GridBagConstraints c = new DefaultGridBagConstraints();
c.gridx = GridBagConstraints.RELATIVE;
c.weightx = 0;
if (title != null && title.trim().length() > 0) {
196,6 → 206,41
}
}
 
private SQLTableModelColumn fieldDebit, fieldCredit;
private SQLTableModelColumn soldeEcrColumn;
 
public void addSubtract(SQLTableModelColumn fieldDebit, SQLTableModelColumn fieldCredit) {
c.weightx = 0;
 
this.fieldCredit = fieldCredit;
this.fieldDebit = fieldDebit;
final JLabelBold comp = new JLabelBold("Solde");
comp.setHorizontalAlignment(SwingConstants.RIGHT);
this.add(comp, c);
JLabelBold textField = new JLabelBold("0");
textField.setHorizontalAlignment(SwingConstants.RIGHT);
this.soldeEcrColumn = new BaseSQLTableModelColumn("SoldeEcr", BigDecimal.class) {
 
@Override
protected Object show_(SQLRowAccessor r) {
// TODO Auto-generated method stub
return null;
}
 
@Override
public Set<FieldPath> getPaths() {
// TODO Auto-generated method stub
return null;
}
};
this.map.put(soldeEcrColumn, textField);
c.weightx = 1;
this.add(textField, c);
c.weightx = 0;
this.add(new JLabelBold(Currency.getSymbol(cc.getCompanyCurrencyCode())), c);
c.gridy++;
}
 
public void fireUpdated() {
for (PropertyChangeListener l : this.loadingListener.getListeners(PropertyChangeListener.class)) {
l.propertyChange(null);
216,10 → 261,13
 
private void computeValues(final List<Tuple2<? extends SQLTableModelColumn, Type>> listField, final List<Tuple2<SQLField, ?>> filters, final List<Tuple2<SQLField, ?>> filtersNot,
final List<ListSQLLine> listLines) {
 
SwingWorker<Tuple3<Map<SQLTableModelColumn, BigDecimal>, Map<SQLTableModelColumn, Double>, Map<SQLTableModelColumn, Integer>>, Object> worker = new SwingWorker<Tuple3<Map<SQLTableModelColumn, BigDecimal>, Map<SQLTableModelColumn, Double>, Map<SQLTableModelColumn, Integer>>, Object>() {
@Override
protected Tuple3<Map<SQLTableModelColumn, BigDecimal>, Map<SQLTableModelColumn, Double>, Map<SQLTableModelColumn, Integer>> doInBackground() throws Exception {
Map<SQLTableModelColumn, BigDecimal> mapTotal = new HashMap<SQLTableModelColumn, BigDecimal>();
Map<SQLTableModelColumn, Double> mapPourcent = new HashMap<SQLTableModelColumn, Double>();
Map<SQLTableModelColumn, Integer> mapPourcentSize = new HashMap<SQLTableModelColumn, Integer>();
 
for (ListSQLLine line : listLines) {
 
final SQLRowAccessor rowAt = line.getRowAccessor();
263,8 → 311,13
} else if (type == Type.AVANCEMENT_TTC) {
 
BigDecimal n = mapTotal.get(field.get0());
BigDecimal ttc = BigDecimal.valueOf(line.getRow().getObjectAs("T_TTC", Number.class).doubleValue());
 
Number objectAs = line.getRow().getObjectAs("T_TTC", Number.class);
BigDecimal ttc;
if (objectAs instanceof Long) {
ttc = BigDecimal.valueOf(objectAs.doubleValue() / 100.0);
} else {
ttc = BigDecimal.valueOf(objectAs.doubleValue());
}
BigDecimal av = BigDecimal.valueOf(((Number) getValueAt(line, field.get0(), columns)).doubleValue());
 
boolean in = true;
287,9 → 340,11
mapTotal.put(field.get0(), n.add(ttc.multiply(av).movePointLeft(2)));
}
}
 
} else if (type != Type.MOYENNE_MARGE && type != Type.COUNT) {
 
// FIXME Test si la colonne existe sinon exception dans liste des articles quand
// FIXME Test si la colonne existe sinon exception dans liste des
// articles quand
// on passe de la vue normal à virtuel
if (columns.indexOf(field.get0()) != -1) {
 
322,7 → 377,18
}
}
}
return Tuple3.create(mapTotal, mapPourcent, mapPourcentSize);
}
 
@Override
protected void done() {
try {
Tuple3<Map<SQLTableModelColumn, BigDecimal>, Map<SQLTableModelColumn, Double>, Map<SQLTableModelColumn, Integer>> tuple3 = get();
 
Map<SQLTableModelColumn, BigDecimal> mapTotal = tuple3.get0();
Map<SQLTableModelColumn, Double> mapPourcent = tuple3.get1();
Map<SQLTableModelColumn, Integer> mapPourcentSize = tuple3.get2();
 
for (Tuple2<? extends SQLTableModelColumn, Type> field : listField) {
if (field.get1() == Type.MOYENNE_MARGE) {
 
350,6 → 416,25
}
}
}
 
if (map.containsKey(soldeEcrColumn)) {
BigDecimal d = mapTotal.get(fieldDebit);
BigDecimal c = mapTotal.get(fieldCredit);
 
if (d != null && c != null) {
map.get(soldeEcrColumn).setText(decimalFormat.format(d.doubleValue() - c.doubleValue()));
} else {
map.get(soldeEcrColumn).setText(decimalFormat.format(0));
}
}
 
fireUpdated();
} catch (InterruptedException | ExecutionException e) {
e.printStackTrace();
}
}
};
worker.execute();
 
}
}
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/AjoutDeclinaisonTableModel.java
162,10 → 162,10
final List<SQLRowAccessor> rowsVariant1 = new ArrayList<SQLRowAccessor>();
final List<SQLRowAccessor> rowsVariant2 = new ArrayList<SQLRowAccessor>();
for (SQLRowValues r : values) {
final SQLRowAccessor v1 = r.getForeign(variant1.getFieldName());
final SQLRowAccessor v1 = r.getNonEmptyForeign(variant1.getFieldName());
if (v1 != null)
rowsVariant1.add(v1);
final SQLRowAccessor v2 = r.getForeign(variant2.getFieldName());
final SQLRowAccessor v2 = r.getNonEmptyForeign(variant2.getFieldName());
if (v2 != null)
rowsVariant2.add(v2);
}
216,8 → 216,8
final Integer[][] tQuantites = new Integer[tNomsVariants1.size()][tNomsVariants2.size()];
final SQLRowValues[][] tArticles = new SQLRowValues[tNomsVariants1.size()][tNomsVariants2.size()];
for (SQLRowValues r : values) {
final SQLRowAccessor v1 = r.getForeign(variant1.getFieldName());
final SQLRowAccessor v2 = r.getForeign(variant2.getFieldName());
final SQLRowAccessor v1 = r.getNonEmptyForeign(variant1.getFieldName());
final SQLRowAccessor v2 = r.getNonEmptyForeign(variant2.getFieldName());
if (v1 != null && v2 != null) {
final Integer idVariant1 = v1.getID();
final Integer idVariant2 = v2.getID();
<
/trunk/OpenConcerto/src/org/openconcerto/erp/core/common/ui/AjoutDeclinaisonButton.java
13,7 → 13,6
package org.openconcerto.erp.core.common.ui;
 
import org.openconcerto.erp.core.finance.tax.model.TaxeCache;
import org.openconcerto.erp.core.sales.product.element.ReferenceArticleSQLElement;
import org.openconcerto.sql.model.DBRoot;
import org.openconcerto.sql.model.SQLField;
40,8 → 39,10
import java.beans.PropertyChangeListener;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
103,6 → 104,19
combo.uiInit(comboModel);
 
p.add(combo, c);
 
final NumericTextField fieldHT = new NumericTextField();
 
List<String> venteItemsTable = Arrays.asList("DEVIS_ELEMENT", "COMMANDE_CLIENT_ELEMENT", "BON_DE_LIVRAISON_ELEMENT", "SAISIE_VENTE_FACTURE_ELEMENT");
if (venteItemsTable.contains(this.itemTable.getSQLElement().getTable().getName())) {
c.gridy++;
c.gridx = 0;
c.weightx = 0;
p.add(new JLabel("Forcer le prix de vente HT à", SwingConstants.RIGHT), c);
c.gridx++;
c.weightx = 1;
p.add(fieldHT, c);
}
// Ligne 2 : table
AjoutDeclinaisonTableModel model = new AjoutDeclinaisonTableModel();
JTable table = new JTable(model);
146,10 → 160,12
 
// Ligne 3: boutons
final JButton bAnnuler = new JButton("Annuler");
final JButton bInserer = new JButton("Insérer");
final JButton bAjouter = new JButton("Ajouter");
final JPanel buttons = new JPanel();
buttons.setLayout(new FlowLayout());
buttons.add(bAnnuler);
buttons.add(bInserer);
buttons.add(bAjouter);
c.anchor = GridBagConstraints.SOUTHEAST;
c.gridy++;
216,22 → 232,49