OpenConcerto

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

svn://code.openconcerto.org/openconcerto

Rev

Rev 180 | Blame | Compare with Previous | Last modification | View Log | RSS feed

/*
 * 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.customerrelationship.customer.element;

import org.openconcerto.erp.core.common.element.ComptaSQLConfElement;
import org.openconcerto.erp.core.common.element.NumerotationAutoSQLElement;
import org.openconcerto.erp.config.Log;

import org.openconcerto.erp.core.common.ui.DeviseField;
import org.openconcerto.erp.core.sales.invoice.element.SaisieVenteFactureSQLElement;
import org.openconcerto.erp.core.sales.invoice.report.VenteFactureXmlSheet;
import org.openconcerto.erp.generationDoc.A4;
import org.openconcerto.erp.generationDoc.ProgressPrintingFrame;
import org.openconcerto.erp.generationDoc.gestcomm.FicheRelanceSheet;
import org.openconcerto.erp.generationDoc.gestcomm.RelanceSheet;
import org.openconcerto.erp.preferences.PrinterNXProps;
import org.openconcerto.sql.element.BaseSQLComponent;
import org.openconcerto.sql.element.SQLComponent;
import org.openconcerto.sql.element.TreesOfSQLRows;
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.sqlobject.ElementComboBox;
import org.openconcerto.sql.sqlobject.JUniqueTextField;
import org.openconcerto.sql.view.EditFrame;
import org.openconcerto.ui.DefaultGridBagConstraints;
import org.openconcerto.sql.view.list.IListe;
import org.openconcerto.sql.view.list.RowAction;
import org.openconcerto.ui.JDate;
import org.openconcerto.ui.component.ITextArea;
import org.openconcerto.ui.component.InteractionMode;
import org.openconcerto.utils.ExceptionHandler;

import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;

import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.print.Paper;
import java.awt.print.PrinterException;
import java.awt.print.PrinterJob;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collections;
import java.util.List;
import java.util.logging.Level;

import javax.print.PrintService;
import javax.print.attribute.Attribute;
import javax.print.attribute.HashPrintRequestAttributeSet;
import javax.print.attribute.Size2DSyntax;
import javax.print.attribute.standard.Copies;
import javax.print.attribute.standard.MediaPrintableArea;
import javax.print.attribute.standard.MediaSizeName;
import javax.swing.AbstractAction;
import javax.swing.JCheckBox;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JSeparator;
import javax.swing.SwingUtilities;
import javax.swing.JOptionPane;
import javax.swing.SwingUtilities;

public class RelanceSQLElement extends ComptaSQLConfElement {
    public static final String ITEM_TYPE = "type.id";
    public static final String ITEM_DATE = "date";
    public static final String ITEM_NUMBER = "number";
    public static final String ITEM_CUSTOMER = "customer.id";
    public static final String ITEM_SALES_INVOICE_INPUT = "sales.invoice.input.id";
    public static final String ITEM_AMOUNT = "amount";
    public static final String ITEM_INFORMATIONS = "informations";
    public static final String ITEM_VISUALIZATION = "visualization";
    public static final String ITEM_PRINT = "impression";
    private static final double POINTS_PER_INCH = 72.0;

    public RelanceSQLElement() {
        super("RELANCE", "une relance client", "relances clients");

        RowAction actionShowDoc = new RowAction(new AbstractAction("Voir le document") {
            public void actionPerformed(ActionEvent e) {
                final RelanceSheet s = new RelanceSheet(IListe.get(e).getSelectedRow().asRow().fetchNew(false));
                s.generate(false, false, "");
                s.showDocument();
            }
        }, false) {
            @Override
            public boolean enabledFor(List<SQLRowValues> selection) {
                if (selection.size() == 1) {
                    SQLRowValues rowRelance = selection.get(0);
                    boolean isNotMail = !(rowRelance.getForeign("ID_TYPE_LETTRE_RELANCE") == null || rowRelance.isForeignEmpty("ID_TYPE_LETTRE_RELANCE"));
                    return isNotMail;
                }
                return false;
            }
        };

        getRowActions().add(actionShowDoc);

        RowAction actionPrintDoc = new RowAction(new AbstractAction("Imprimer") {
            public void actionPerformed(ActionEvent e) {
                print(e, false);
            }
        }, false) {
            @Override
            public boolean enabledFor(List<SQLRowValues> selection) {
                if (selection.size() >= 1) {
                    boolean isNotMail = true;
                    for (SQLRowValues rowRelance : selection) {

                        isNotMail &= !(rowRelance.getForeign("ID_TYPE_LETTRE_RELANCE") == null || rowRelance.isForeignEmpty("ID_TYPE_LETTRE_RELANCE"));
                    }
                    return isNotMail;
                }
                return false;
            }
        };

        getRowActions().add(actionPrintDoc);

        // Impression

        RowAction actionPrintDocFact = new RowAction(new AbstractAction("Imprimer avec la facture") {
            public void actionPerformed(ActionEvent e) {
                print(e, true);
            }
        }, false) {
            @Override
            public boolean enabledFor(List<SQLRowValues> selection) {
                if (selection.size() >= 1) {
                    boolean isNotMail = true;
                    for (SQLRowValues rowRelance : selection) {

                        isNotMail &= !(rowRelance.getForeign("ID_TYPE_LETTRE_RELANCE") == null || rowRelance.isForeignEmpty("ID_TYPE_LETTRE_RELANCE"));
                    }
                    return isNotMail;
                }
                return false;
            }
        };

        getRowActions().add(actionPrintDocFact);

        // Générer

        RowAction actionGen = new RowAction(new AbstractAction("Générer le document") {
            public void actionPerformed(ActionEvent e) {

                for (SQLRowValues rowVals : IListe.get(e).getSelectedRows()) {
                    final RelanceSheet s = new RelanceSheet(rowVals.asRow().fetchNew(false));
                    String printer = PrinterNXProps.getInstance().getStringProperty("RelancePrinter");
                    s.generate(false, true, printer, true);
                    s.showDocument();
                }
            }
        }, false) {
            @Override
            public boolean enabledFor(List<SQLRowValues> selection) {
                if (selection.size() >= 1) {
                    SQLRowValues rowRelance = selection.get(0);
                    boolean isNotMail = !(rowRelance.getForeign("ID_TYPE_LETTRE_RELANCE") == null || rowRelance.isForeignEmpty("ID_TYPE_LETTRE_RELANCE"));
                    return isNotMail;
                }
                return false;
            }
        };

        getRowActions().add(actionGen);

        RowAction actionFiche = new RowAction(new AbstractAction("Créer la fiche de relance") {
            public void actionPerformed(ActionEvent e) {
                try {
                    FicheRelanceSheet sheet = new FicheRelanceSheet(IListe.get(e).getSelectedRow().asRow().fetchNew(false));
                    sheet.createDocumentAsynchronous();
                    sheet.showPrintAndExportAsynchronous(true, false, true, Collections.emptyList());
                } catch (Exception ex) {
                    ExceptionHandler.handle("Impression impossible", ex);
                }
            }
        }, false) {
            @Override
            public boolean enabledFor(List<SQLRowValues> selection) {
                return (selection.size() == 1);
            }
        };

        getRowActions().add(actionFiche);

    }

    protected List<String> getListFields() {
        final List<String> l = new ArrayList<String>();
        l.add("NUMERO");
        l.add("ID_CLIENT");
        l.add("ID_SAISIE_VENTE_FACTURE");
        l.add("DATE");
        l.add("ID_TYPE_LETTRE_RELANCE");
        l.add("MONTANT");
        l.add("INFOS");
        return l;
    }

    protected List<String> getComboFields() {
        final List<String> l = new ArrayList<String>();
        l.add("NUMERO");
        return l;
    }

    /*
     * (non-Javadoc)
     * 
     * @see org.openconcerto.devis.SQLElement#getComponent()
     */
    public SQLComponent createComponent() {
        return new BaseSQLComponent(this) {

            ElementComboBox comboFacture = new ElementComboBox();
            ElementComboBox comboClient = new ElementComboBox();
            ElementComboBox comboTypeLettre;
            JUniqueTextField textNumero = new JUniqueTextField();
            JCheckBox checkImpression = new JCheckBox("Impression");
            JCheckBox checkVisu = new JCheckBox("Visualisation");

            public void addViews() {

                this.setLayout(new GridBagLayout());
                final GridBagConstraints c = new DefaultGridBagConstraints();

                // Type lettre
                JLabel labelTypeLettre = new JLabel(getLabelFor("ID_TYPE_LETTRE_RELANCE"));
                labelTypeLettre.setHorizontalAlignment(JLabel.RIGHT);
                this.add(labelTypeLettre, c);

                c.gridx++;
                // SQLElement typeLettreElt =
                // Configuration.getInstance().getDirectory().getElement("TYPE_LETTRE_RELANCE");
                this.comboTypeLettre = new ElementComboBox(false);

                this.add(this.comboTypeLettre, c);

                // Date
                c.gridx++;
                JLabel labelDate = new JLabel(getLabelFor("DATE"));
                labelDate.setHorizontalAlignment(JLabel.RIGHT);
                this.add(labelDate, c);

                JDate date = new JDate(true);
                c.gridx++;
                this.add(date, c);

                // Numero
                c.gridx = 0;
                c.gridy++;
                JLabel labelNumero = new JLabel(getLabelFor("NUMERO"));
                labelNumero.setHorizontalAlignment(JLabel.RIGHT);
                this.add(labelNumero, c);

                c.gridx++;
                this.add(this.textNumero, c);

                // Client
                c.gridy++;
                c.gridx = 0;

                JLabel labelClient = new JLabel(getLabelFor("ID_CLIENT"));
                labelClient.setHorizontalAlignment(JLabel.RIGHT);
                this.add(labelClient, c);
                c.gridx++;
                c.gridwidth = GridBagConstraints.REMAINDER;
                this.add(this.comboClient, c);

                // Facture
                c.gridy++;
                c.gridx = 0;
                c.gridwidth = 1;
                JLabel labelFacture = new JLabel(getLabelFor("ID_SAISIE_VENTE_FACTURE"));
                labelFacture.setHorizontalAlignment(JLabel.RIGHT);
                this.add(labelFacture, c);
                c.gridx++;
                // c.gridwidth = GridBagConstraints.REMAINDER;
                this.add(this.comboFacture, c);

                // Montant
                c.gridx++;
                JLabel labelMontant = new JLabel(getLabelFor("MONTANT"));
                labelMontant.setHorizontalAlignment(JLabel.RIGHT);
                this.add(labelMontant, c);

                c.gridx++;
                DeviseField textMontant = new DeviseField();
                this.add(textMontant, c);

                // Commentaires
                c.gridx = 0;
                c.gridy++;
                this.add(new JLabel(getLabelFor("INFOS")), c);

                c.gridx++;
                c.gridwidth = GridBagConstraints.REMAINDER;
                c.fill = GridBagConstraints.HORIZONTAL;
                c.weightx = 1;
                this.add(new JSeparator(JSeparator.HORIZONTAL), c);

                c.gridx = 0;
                c.gridy++;
                c.weighty = 1;
                c.fill = GridBagConstraints.BOTH;
                ITextArea textInfos = new ITextArea();
                this.add(textInfos, c);

                JPanel panelCheck = new JPanel();
                panelCheck.setBorder(null);
                panelCheck.add(this.checkVisu);
                panelCheck.add(this.checkImpression);
                c.fill = GridBagConstraints.NONE;
                c.weighty = 0;
                c.gridy++;
                this.add(panelCheck, c);

                this.addRequiredSQLObject(textMontant, "MONTANT");
                this.addRequiredSQLObject(date, "DATE");
                this.addRequiredSQLObject(this.comboTypeLettre, "ID_TYPE_LETTRE_RELANCE");
                this.addRequiredSQLObject(this.comboClient, "ID_CLIENT");
                this.addRequiredSQLObject(this.comboFacture, "ID_SAISIE_VENTE_FACTURE");
                this.addSQLObject(textInfos, "INFOS");
                this.addRequiredSQLObject(this.textNumero, "NUMERO");
                this.comboTypeLettre.setButtonsVisible(false);

                this.textNumero.setText(NumerotationAutoSQLElement.getNextNumero(RelanceSQLElement.class));
                this.checkVisu.setSelected(true);
            }

            @Override
            public int insert(SQLRow order) {

                if (this.textNumero.checkValidation()) {
                    // incrémentation du numéro auto
                    if (NumerotationAutoSQLElement.getNextNumero(RelanceSQLElement.class).equalsIgnoreCase(this.textNumero.getText().trim())) {
                        SQLTable tableNum = getTable().getBase().getTable("NUMEROTATION_AUTO");
                        SQLRowValues rowVals = new SQLRowValues(tableNum);
                        int val = tableNum.getRow(2).getInt("RELANCE_START");
                        val++;
                        rowVals.put("RELANCE_START", Integer.valueOf(val));

                        try {
                            rowVals.update(2);
                        } catch (SQLException e) {

                            e.printStackTrace();
                        }
                    }

                    // insertion
                    int id = super.insert(order);

                    // génération du document
                    RelanceSheet s = new RelanceSheet(getTable().getRow(id));
                    String printer = PrinterNXProps.getInstance().getStringProperty("RelancePrinter");
                    s.generate(this.checkImpression.isSelected(), this.checkVisu.isSelected(), printer, true);

                    return id;
                } else {
                    ExceptionHandler.handle("Impossible d'ajouter, numéro de relance existant.");
                    Object root = SwingUtilities.getRoot(this);
                    if (root instanceof EditFrame) {
                        EditFrame frame = (EditFrame) root;
                        frame.getPanel().setAlwaysVisible(true);
                    }
                    return getSelectedID();
                }
            }

            @Override
            public void select(SQLRowAccessor r) {
                super.select(r);

                // numero de facture et client figé
                this.comboFacture.setInteractionMode(InteractionMode.DISABLED);
                this.comboClient.setInteractionMode(InteractionMode.DISABLED);
                this.fireValidChange();
            }

            @Override
            public void update() {
                if (!this.textNumero.checkValidation()) {
                    ExceptionHandler.handle("Impossible d'ajouter, numéro de relance existant.");
                    Object root = SwingUtilities.getRoot(this);
                    if (root instanceof EditFrame) {
                        EditFrame frame = (EditFrame) root;
                        frame.getPanel().setAlwaysVisible(true);
                    }
                    return;
                }

                super.update();

                // regénération du document
                RelanceSheet s = new RelanceSheet(getTable().getRow(getSelectedID()));
                String printer = PrinterNXProps.getInstance().getStringProperty("RelancePrinter");
                s.generate(this.checkImpression.isSelected(), this.checkVisu.isSelected(), printer);
            }

        };
    }

    @Override
    protected void archive(TreesOfSQLRows trees, boolean cutLinks) throws SQLException {

        for (SQLRow row : trees.getRows()) {
            if (row.getForeign("ID_ECHEANCE_CLIENT") != null && !row.isForeignEmpty("ID_ECHEANCE_CLIENT")) {
                SQLRow rowEch = row.getForeign("ID_ECHEANCE_CLIENT");
                int count = rowEch.getInt("NOMBRE_RELANCE");
                count = Math.max(0, count - 1);

                SQLRowValues rowValsUp = rowEch.createEmptyUpdateRow();
                rowValsUp.put("NOMBRE_RELANCE", count);
                rowValsUp.put("DATE_LAST_RELANCE", null);
                if (count > 0) {
                    List<SQLRow> rows = rowEch.getReferentRows(row.getTable());
                    Calendar cal = null;
                    for (SQLRow sqlRow : rows) {
                        if (sqlRow.getID() != row.getID() && sqlRow.getDate("DATE") != null && (cal == null || cal.before(sqlRow.getDate("DATE")))) {
                            cal = sqlRow.getDate("DATE");
                        }
                    }
                    if (cal != null) {
                        rowValsUp.put("DATE_LAST_RELANCE", cal.getTime());
                    }
                }
                rowValsUp.commit();
            }
        }
        super.archive(trees, cutLinks);
    }

    @Override
    protected String createCode() {
        return this.createCodeOfPackage() + ".chaseletter";
    }

    public void print(final ActionEvent ev, boolean withInvoice) {
        //
        final IListe ilist = IListe.get(ev);
        String printerName = PrinterNXProps.getInstance().getStringProperty("RelancePrinter");
        // Printer configuration
        final PrinterJob printJob = PrinterJob.getPrinterJob();

        // Set the printer
        PrintService myService = null;
        if (printerName != null && printerName.trim().length() > 0) {
            final PrintService[] services = PrinterJob.lookupPrintServices();
            for (int i = 0; i < services.length; i++) {
                if (services[i].getName().equals(printerName)) {
                    myService = services[i];
                    break;
                }
            }
            if (myService != null) {
                try {
                    printJob.setPrintService(myService);
                } catch (PrinterException e) {
                    Log.get().log(Level.SEVERE, "cannot print", e);
                    JOptionPane.showMessageDialog(null, "Imprimante non compatible");
                    return;
                }
            }
        }

        final HashPrintRequestAttributeSet attributes = new HashPrintRequestAttributeSet();
        // L'impression est forcée en A4, sur OpenSuse le format est en
        // Letter par défaut alors que l'imprimante est en A4 dans le système
        final MediaSizeName media = MediaSizeName.ISO_A4;
        attributes.add(media);
        Paper paper = new A4(0, 0);

        final MediaPrintableArea printableArea = new MediaPrintableArea((float) (paper.getImageableX() / POINTS_PER_INCH), (float) (paper.getImageableY() / POINTS_PER_INCH),
                (float) (paper.getImageableWidth() / POINTS_PER_INCH), (float) (paper.getImageableHeight() / POINTS_PER_INCH), Size2DSyntax.INCH);
        attributes.add(printableArea);
        attributes.add(new Copies(1));

        boolean okToPrint = printJob.printDialog(attributes);
        final Attribute attribute = attributes.get(Copies.class);
        if (attribute != null) {
            final Copies attributeCopies = (Copies) attribute;
            final int value = attributeCopies.getValue();
            printJob.setCopies(value);
        } else {
            printJob.setCopies(1);
        }

        if (okToPrint) {
            Window w = SwingUtilities.getWindowAncestor(ilist);
            final ProgressPrintingFrame pFrame = new ProgressPrintingFrame(w, printJob, "Impression", "Impression en cours", 300);
            // Génération + impression
            final List<SQLRowValues> rows = IListe.get(ev).getSelectedRows();
            final Thread thread = new Thread() {
                @Override
                public void run() {
                    final int size = rows.size();
                    for (int i = 0; i < size; i++) {
                        final int index = i;
                        SwingUtilities.invokeLater(new Runnable() {

                            @Override
                            public void run() {
                                pFrame.setMessage("Document " + (index + 1) + "/" + size);
                                pFrame.setProgress((100 * (index + 1)) / size);
                            }
                        });
                        if (!pFrame.isCancelled()) {
                            SQLRowValues r = rows.get(i);
                            SQLRow rowRelance = r.asRow().fetchNew(false);
                            RelanceSheet s = new RelanceSheet(rowRelance);
                            s.printDocument(printJob);
                            if (withInvoice) {
                                SaisieVenteFactureSQLElement element = getDirectory().getElement(SaisieVenteFactureSQLElement.class);
                                final VenteFactureXmlSheet sheet = new VenteFactureXmlSheet(rowRelance.getForeignRow("ID_SAISIE_VENTE_FACTURE"));
                                try {
                                    sheet.getOrCreateDocumentFile();
                                    sheet.printDocument(printJob);
                                } catch (Exception e) {
                                    ExceptionHandler.handle("Erreur lors de la création de la facture", e);
                                }
                            }

                        }
                    }
                }
            };
            thread.setPriority(Thread.MIN_PRIORITY);
            thread.setDaemon(true);
            pFrame.setLocationRelativeTo(ilist);
            pFrame.setVisible(true);
            thread.start();

        }

    }
}