campo-sirio/lv/lv3200.cpp
luca83 93a0b47104 Patch level : 10.0 patch 548
Files correlati     : lv2 lv3
Ricompilazione Demo : [ ]
Commento            :
Aggiungere nell'acquisizione da contapezzi articolo inesistente in contratto

Creazione buoni di prelievo in ordine di codice articolo


git-svn-id: svn://10.65.10.50/trunk@19785 c028cbd2-c16b-5b4b-a496-9718f37d4682
2009-12-15 15:38:34 +00:00

1284 lines
36 KiB
C++
Executable File

#include <applicat.h>
#include <automask.h>
#include <defmask.h>
#include <execp.h>
#include <reputils.h>
#include <reprint.h>
#include <utility.h>
#include "lvlib.h"
#include "../mg/clifogiac.h"
#include "../ve/velib.h"
#include "clifo.h"
#include "lvcondv.h"
#include "lvrcondv.h"
#include "lvrconsplan.h"
#include "lv3200a.h"
/////////////////////////////
//// TEVASIONE_MSK ////
/////////////////////////////
//classe TEvasione_msk
class TEvasione_msk: public TAutomask
{
TDocumento _buonori;
int _ndoc;
int _autoselect;
TString4 _tpev;
TAssoc_array _pacchi;
protected:
void setta_campi_data();
void setta_campi_cliente();
void carica_righe();
void riordina_righe();
void genera_documento();
void evadi_tutto();
void spezza_riga();
void salva();
void annulla_operazioni();
bool controlla();
void sistema_quantita();
void sistema_pacchi();
void evadi_da_barcode();
virtual void on_idle();
virtual bool on_field_event(TOperable_field& o, TField_event e, long jolly);
public:
TEvasione_msk();
};
//SORT_BY_QTA_EVASA: è la rows_comapre_function, cioè la funzione che viene utilizzata
//dal metodo sort degli sheet per riordinare le righe secondo le quantità evase
static int sort_by_qta_evasa(TSheet_field& sheet, int r1, int r2)
{
TToken_string& row1 = sheet.row(r1);
TToken_string& row2 = sheet.row(r2);
const int qta1 = row1.get_int(6);
const int qta2 = row2.get_int(6);
int dif = qta1 - qta2;
if (dif == 0)
{
const TString& codart1 = row1.get(1);
const TString& codart2 = row2.get(1);
dif = codart1.compare(codart2);
}
return dif;
}
//SORT_BY_CODART: è la rows_comapre_function, cioè la funzione che viene utilizzata
//dal metodo sort degli sheet per riordinare le righe secondo i codart e le qta evase
static int sort_by_codart(TSheet_field& sheet, int r1, int r2)
{
TToken_string& row1 = sheet.row(r1);
TToken_string& row2 = sheet.row(r2);
const TString& codart1 = row1.get(1);
const TString& codart2 = row2.get(1);
int dif = codart1.compare(codart2);
if (dif == 0)
{
const int qta1 = row1.get_int(6);
const int qta2 = row2.get_int(6);
dif = qta2 - qta1;
}
return dif;
}
//SETTA_CAMPI_DATA: metodo che compila tutti i campi legati alla data
void TEvasione_msk::setta_campi_data()
{
TDate data = get_date(F_DATADOC);
if (data.ok())
{
TDate primo = data;
primo.set_day(1);
TEsercizi_contabili es;
int annoes = es.date2esc(data);
set(F_ANNO, annoes);
//decodifica del giorno della settimana
set(F_GIORNO, itow(data.wday()));
//settimana del mese = settimana(oggi) - settimana(primo del mese) + 1
long tmp = data.week() - primo.week() + 1;
TString4 settimana;
settimana << tmp;
set(F_SETTIMANA, settimana);
}
else
{
TString8 str = data.string();
if (str.empty())
{
reset(F_GIORNO);
reset(F_SETTIMANA);
}
else
warning_box(TR("Data non valida!"));
}
}
//SETTA_CAMPI_CLIENTE: metodo che compila tutti i campi legati al cliente
void TEvasione_msk::setta_campi_cliente()
{
const long codcf = get_int(F_CODCF);
const TDate data = get_date(F_DATADOC);
if (codcf > 0)
{
TToken_string key;
key.add('C');
key.add(codcf);
const int codindsp = atoi(cache().get(LF_CFVEN, key, CFV_CODINDSP));
TLaundry_contract cont(codcf, codindsp, data);
//se trovo un contratto, allora scrivo il codice contratto e cerco itinerario e data di prevista consegna
//se no avviso che non c'è neanche un contratto valido e svuoto i campi interassati
if(!cont.empty())
{
set(F_CODCONT, cont.get_int(LVCONDV_CODCONT));
TDate adata = data;
adata.addmonth(1);
TString query = "USE LVRCONSPLAN KEY 3\n";
query << "FROM CODCF=" << get(F_CODCF) << " CODCONT=" << get(F_CODCONT) << " DTCONS=" << data << "\n";
query << "TO CODCF=" << get(F_CODCF) << " CODCONT=" << get(F_CODCONT) << " DTCONS=" << adata << "\n";
TISAM_recordset consegne(query);
if (consegne.items() >= 2)
{
consegne.move_to(1);
set(F_DATAPRCO, consegne.get(LVRCONSPLAN_DTCONS).as_date());
set(F_CODITI, consegne.get(LVRCONSPLAN_CODITI).as_int());
}
else
{
reset(F_DATAPRCO);
reset(F_CODITI);
}
if (get(F_RAGSOC).empty())
{
TToken_string key;
key.add('C');
key.add(codcf);
const TRectype& clifo = cache().get(LF_CLIFO, key);
set(F_RAGSOC, clifo.get(CLI_RAGSOC));
set(F_RICALT, clifo.get(CLI_RICALT));
}
}
else
{
TString msg;
msg << "ATTENZIONE: nessun contratto in essere per il cliente " << codcf << " alla data " << data;
warning_box(msg);
reset(F_CODCONT);
reset(F_DATAPRCO);
reset(F_CODITI);
}
}
else
{
reset(F_RICALT);
reset(F_RAGSOC);
reset(F_CODCONT);
reset(F_DATAPRCO);
reset(F_CODITI);
}
}
//CARICA_RIGHE: metodo che carica sullo sheet le righe di un documento selezionato
void TEvasione_msk::carica_righe()
{
TDoc_key kdoc(get_int(F_ANNO), get(F_CODNUM), get_long(F_NDOC));
TBuono_prelievo doc(kdoc);
const TString4 stato = doc.get(DOC_STATO);
const TString4 steva = cache().get("%TIP", ini_get_string(CONFIG_DITTA, "lv", "TIPODOC_PRE", NULL, 0), "S2").mid(2,1);
if (stato == steva)
{
TString str;
str << "Il documento " << get_long(F_NDOC) << " è già stato evaso";
warning_box(str);
set(F_NDOC, 0L, 1);
return;
}
set(F_STATO, stato);
disable(F_STATO);
set(F_DATABOLLA, doc.get_date(DOC_DATADOC));
set(F_DATADOC, doc.get_date(DOC_DATADOC)); setta_campi_data();
set(F_CODCF, doc.get_long(DOC_CODCF)); setta_campi_cliente(); field(F_CODCF).set_dirty();
_buonori = doc;
_pacchi.destroy();
if(doc.rows() > 0)
{
enable(DLG_SELECT);
enable(DLG_PREVIEW);
if(stato == "2")
enable(DLG_ELABORA);
enable(DLG_SAVEREC);
enable(DLG_CANCEL);
show(F_RIGHE);
}
TSheet_field& sheet = sfield(F_RIGHE);
for(int i = 1; i <= doc.rows(); i++)
{
TRiga_documento& row = doc[i];
TBuono_prelievo_row rdoc(row);
if (rdoc.qta_dacons() > 0)
{
TToken_string& riga = sheet.row(-1);
riga.add(rdoc.evaso() ? "X" : "", sheet.cid2index(S_EVASO));
riga.add(rdoc.codart(), sheet.cid2index(S_CODART));
riga.add(rdoc.desart(), sheet.cid2index(S_ARTDESCR));
riga.add(rdoc.causale(), sheet.cid2index(S_CAUSALE));
riga.add(rdoc.qta_ritirata(), sheet.cid2index(S_RITIRATO));
riga.add(rdoc.qta_dacons(), sheet.cid2index(S_DACONS));
riga.add(rdoc.qta_consegnata(), sheet.cid2index(S_CONSEGNATO));
const TRectype& anamag = cache().get(LF_ANAMAG, rdoc.codart());
//recupero i dati di interesse dall'anagrafica di magazzino
const long ppconf = anamag.get_long(ANAMAG_PPCONF);
if (ppconf > 0)
riga.add(rdoc.num_pacchi(), sheet.cid2index(S_PACCHI));
else
{
riga.add(0, sheet.cid2index(S_PACCHI));
sheet.disable_cell(i, sheet.cid2index(S_PACCHI));
}
riga.add(rdoc.cong_pre(), sheet.cid2index(S_CONGPRE));
riga.add(rdoc.cong_att(), sheet.cid2index(S_CONGATT));
riga.add(rdoc.rifbcon(), sheet.cid2index(S_RIFBCON));
}
else
rdoc.set_evaso(true);
}
doc.rewrite();
sheet.sort(sort_by_codart);
FOR_EACH_SHEET_ROW(sheet, r, row)
{
if (row->get_char(0) == 'X')
sheet.disable_row(r);
}
sheet.force_update();
}
//RIORDINA_RIGHE: metodo che riordina le righe dello sheet in base alle quota di evasione
void TEvasione_msk::riordina_righe()
{
TSheet_field& sheet = sfield(F_RIGHE);
sheet.sort(sort_by_qta_evasa);
sheet.force_update();
}
//GENERA_DOCUMENTO: metodo che genera il buono di consegna partendo dal buono di ritiro
void TEvasione_msk::genera_documento()
{
//per prima cosa salva il buono di prelievo
salva();
TDoc_key kdoc(get_int(F_ANNO), get(F_CODNUM), get_long(F_NDOC));
TBuono_prelievo bpre(kdoc);
const long codcf = bpre.codcf();
const int codcont = bpre.codcont();
TLaundry_contract cont(codcf, codcont);
//leggo se devo scrivere il prezzo sulla bolla
//const bool prinbo = cont.get_bool(LVCONDV_STPRZBOL);
const bool prinbo = true; //sempre a true; verrà gestita a video in futuro (27/10/2009)
//dati documento da generare
TString4 codnum;
TString4 tipodoc;
if (cont.get(LVCONDV_CODNUM).empty())
{
codnum = ini_get_string(CONFIG_DITTA, "lv", "NUM_GEN");
tipodoc = ini_get_string(CONFIG_DITTA, "lv", "TIPODOC_GEN");
}
else
{
codnum = cont.get(LVCONDV_CODNUM);
tipodoc = cont.get(LVCONDV_TPDOC);
}
char stato = cache().get("%TIP", tipodoc, "S2").left(1)[0];
const TDate databpre = bpre.datadoc();
const TDate databolla = get_date(F_DATABOLLA);
const TDate datagen(TODAY);
TDate dadata = databpre;
TDate adata = datagen;
adata.addmonth();
if(_ndoc == 0)
{
TString query2;
query2 << "USE DOC\n"
<< "FROM PROVV=\"D\" ANNO=" << datagen.year() << " CODNUM=\"" << codnum << "\"\n"
<< "TO PROVV=\"D\" ANNO=" << datagen.year() << " CODNUM=\"" << codnum << "\"";
TISAM_recordset bolle(query2);
if (bolle.move_last())
_ndoc = bolle.get(DOC_NDOC).as_int();
}
TString query1 = "USE LVRCONSPLAN KEY 3\n";
query1 << "FROM CODCF=" << codcf << " CODCONT=" << codcont << " DTCONS=#DADATA\n";
query1 << "TO CODCF=" << codcf << " CODCONT=" << codcont << " DTCONS=#ADATA\n";
TISAM_recordset consegne(query1);
consegne.set_var("#DADATA", ++dadata);
consegne.set_var("#ADATA", adata);
consegne.move_first();
const TDate dataprco = consegne.get(LVRCONSPLAN_DTCONS).as_date();
const int coditi = consegne.get(LVRCONSPLAN_CODITI).as_int();
const long codaut = consegne.get(LVRCONSPLAN_CODAUT).as_int();
//recupero il codpag
TToken_string key;
key.add('C');
key.add(codcf);
const TRectype& clifo = cache().get(LF_CLIFO, key);
const TString4 codpag = clifo.get(CLI_CODPAG);
const long codabi = clifo.get_long(CLI_CODABI);
const long codcab = clifo.get_long(CLI_CODCAB);
const TString80 iban = clifo.get(CLI_IBAN);
//reupero la cuasale di magazzino di testata
const TString16 causmag = cache().get("%TIP", tipodoc, "S9");
//recupero i dati di interesse dal file CFVEN
const TRectype& cfven = cache().get(LF_CFVEN, key);
const long codabipr = cfven.get_long(CFV_CODABIPR);
const long codcabpr = cfven.get_long(CFV_CODCABPR);
const bool ragdoc = cfven.get_bool(CFV_RAGGDOC);
const int codindsp = cfven.get_int(CFV_CODINDSP);
const TString8 codag1 = cfven.get(CFV_CODAG1);
const TString4 codmez = cfven.get(CFV_CODSPMEZZO);
const TString4 codporto = cfven.get(CFV_CODPORTO);
const TString4 codnote1 = cfven.get(CFV_CODNOTESP1);
const TString4 codnote2 = cfven.get(CFV_CODNOTESP2);
const TString4 codnote = cfven.get(CFV_CODNOTE);
const TString8 codvet1 = cfven.get(CFV_CODVETT1);
const TString8 codvet2 = cfven.get(CFV_CODVETT2);
const TString8 codvet3 = cfven.get(CFV_CODVETT3);
const real speseinc = cfven.get_real(CFV_PERCSPINC);
const TString4 catven = cfven.get(CFV_CATVEN);
const bool addbolli = cfven.get_bool(CFV_ADDBOLLI);
const TString8 codlist = cfven.get(CFV_CODLIST);
const TString4 codzona = cfven.get(CFV_CODZONA);
//gestione sconto
TString sconto;
const char tpgest = ini_get_string(CONFIG_DITTA, "ve", "GESSCO")[0];
switch(tpgest)
{
case 'P': sconto = cfven.get(CFV_CODSCC); break; //Percentuale su anagrafica cliente
case 'T': sconto = cache().get("%SCC", cfven.get(CFV_CODSCC), "S1"); break; //Gestione tabella sconti
case 'A': //Gestione archivio sconti
{
TConfig ditta(CONFIG_DITTA, "ve");
TLocalisamfile sconti(LF_SCONTI);
sconti.put("TIPO", "I");
if(ditta.get_bool("SCOKEY", "ve", 1))
sconti.put("CODCAT", cfven.get(CFV_CATVEN));
TString16 cod;
if(ditta.get_bool("SCOKEY", "ve", 2))
cod.format("%-2s", (const char*)cfven.get(CFV_CODSCC));
else
cod = " ";
if(ditta.get_bool("SCOKEY", "ve", 3))
{
TString8 tmp;
tmp.format("%-2s", (const char*)cfven.get(CFV_CODZONA));
cod << tmp;
}
else
cod << " ";
if(ditta.get_bool("SCOKEY", "ve", 4))
cod << clifo.get(CLI_CODPAG);
sconti.put("CODART", cod);
if (sconti.read() == NOERR)
sconto = sconti.get("SCONTO");
}
case 'N': //sconto non gestito
default: break;
}
//preparo la testata del documento
TDocumento doc('D', kdoc.anno(), codnum, ++_ndoc);
doc.put(DOC_TIPODOC, tipodoc);
doc.put(DOC_STATO, stato);
doc.put(DOC_DATADOC, databolla);
doc.put(DOC_TIPOCF, 'C');
doc.put(DOC_CODCF, codcf);
doc.put(DOC_CODCONT, codcont);
doc.put(DOC_CODPAG, codpag);
doc.put(DOC_CODINDSP, codindsp);
doc.put(DOC_CODABIA, codabi);
doc.put(DOC_CODCABA, codcab);
doc.put(DOC_IBAN, iban);
doc.put(DOC_CODABIP, codabipr);
doc.put(DOC_CODCABP, codcabpr);
doc.put(DOC_CODAG, codaut);
doc.put(DOC_CODAGVIS, codag1);
doc.put(DOC_CODSPMEZZO, codmez);
doc.put(DOC_ZONA, codzona);
doc.put(DOC_CODPORTO, codporto);
doc.put(DOC_CODNOTESP1, codnote1);
doc.put(DOC_CODNOTESP2, codnote2);
doc.put(DOC_CODNOTE, codnote);
doc.put(DOC_CODVETT1, codvet1);
doc.put(DOC_CODVETT2, codvet2);
doc.put(DOC_CODVETT3, codvet3);
doc.put(DOC_CATVEN, catven);
doc.put(DOC_CODLIST, codlist);
doc.put(DOC_CAUSMAG, causmag);
doc.put(DOC_PERCSPINC, speseinc);
doc.put(DOC_ADDBOLLI, addbolli);
doc.put(DOC_SCONTOPERC, sconto);
doc.put("DATAGEN", datagen); //data generazione del documento
doc.put("DATAPRCO", dataprco); //data prevista consegna
doc.put("CODITI", coditi); //codice itinerario
for (int i = 1; i <= bpre.rows(); i++)
{
TRiga_documento& row = bpre[i];
TBuono_prelievo_row rbpre(row);
//nella bolla ci vanno solo le righe evase e non associate
if (!rbpre.evaso())
continue;
TDoc_key kbuono = rbpre.rifbcon();
if (kbuono.full())
continue;
const TString80 codart = rbpre.codart();
TString descr = rbpre.desart();
const TRectype& rcont = cont.row(codart);
//recupero i valori delle dotazione temporanea dal magazzino del cliente
TLocalisamfile magcli(LF_CLIFOGIAC);
magcli.put(CLIFOGIAC_ANNOES, datagen.year());
magcli.put(CLIFOGIAC_TIPOCF, 'C');
magcli.put(CLIFOGIAC_CODCF, codcf);
magcli.put(CLIFOGIAC_INDSPED, 0); //in realtà è da leggere dal contratto
magcli.put(CLIFOGIAC_CODART, codart);
magcli.put(CLIFOGIAC_NRIGA, 1);
//leggo il record corrispondente
magcli.read();
long dottmp = magcli.get_long(CLIFOGIAC_DOTTM);
long dotod = magcli.get_long(CLIFOGIAC_DOTOD);
//recupero l'unità di misura principale di quest'articolo
TToken_string key;
key.add(codart);
key.add(1);
const TString4 um = cache().get(LF_UMART, key, UMART_UM);
TRiga_documento& rdoc = doc.new_row("21");
rdoc.put(RDOC_CODART, codart);
rdoc.put(RDOC_CODARTMAG,codart);
rdoc.put(RDOC_CHECKED,'X');
rdoc.put(RDOC_GENERATA, true);
if(descr.len() <= 50)
rdoc.put(RDOC_DESCR, descr);
else
{
rdoc.put(RDOC_DESCR, descr.left(50));
rdoc.put(RDOC_DESCEST, descr.sub(50));
rdoc.put(RDOC_DESCLUNGA, true);
}
rdoc.put(RDOC_QTA, rbpre.qta_consegnata()); //consegnato
rdoc.put(RDOC_QTAGG1, rbpre.qta_ritirata()); //ritirato
dotod += (rbpre.qta_consegnata() - rbpre.qta_ritirata());
rdoc.put("DOTOD", dotod);
bool dtmp = false;
if (datagen >= rcont.get_date(LVRCONDV_INDTTMP) && datagen <= rcont.get_date(LVRCONDV_FIDTTMP))
dtmp = true;
if(dtmp)
{
rdoc.put("DOTMP", dottmp);
rdoc.add("DOTMP", rbpre.qta_consegnata() - rbpre.qta_ritirata());
}
rdoc.put(RDOC_CODAGG1, rbpre.causale());
const TRectype& anamag = cache().get(LF_ANAMAG, codart);
//gestione prezzo
if (prinbo)
{
real prezzo;
if (cont.get_int(LVCONDV_TIPOLIS) == 0)
prezzo = rcont.get_real(LVRCONDV_PREZZO);
else
prezzo = anamag.get_real(ANAMAG_COSTSTD);
rdoc.put(RDOC_PREZZO, prezzo);
rdoc.put(RDOC_SCONTO, rcont.get(LVRCONDV_SCONTPERC)); //sconto
}
rdoc.put(RDOC_UMQTA, um);
//scrivo il magazzino
TString8 magazzino;
TString8 magazzinoc;
magazzino << ini_get_string(CONFIG_DITTA, "lv", "CODMAG") << ini_get_string(CONFIG_DITTA, "lv", "CODMAGN");
magazzinoc << ini_get_string(CONFIG_DITTA, "lv", "CODMAG") << ini_get_string(CONFIG_DITTA, "lv", "CODMAGC");
rdoc.put(RDOC_CODMAG, magazzino);
rdoc.put(RDOC_CODMAGC, magazzinoc);
//salvo i riferimenti
TDoc_key rifbcon(datagen.year(), codnum, _ndoc);
rbpre.set_rifbcon(rifbcon);
}
//salva la bolla solo se ha almeno una riga
int err = 1;
if (doc.rows() > 0)
{
TToken_string orderkey;
orderkey.add(RDOC_CODART);
doc.sort_rows(orderkey);
err = doc.write();
if(controlla())
{
const TString4 stato = cache().get("%TIP", ini_get_string(CONFIG_DITTA, "lv", "TIPODOC_PRE", NULL, 0), "S2").mid(2,1);
bpre.put(DOC_STATO, stato);
bpre.rewrite();
set(F_STATO, stato);
}
}
if (err == NOERR)
{
if (yesno_box(TR("Il documento è stato generato; si desiderla stamparlo?")))
{
//stampa automatica
TString80 str;
str << "ve1 -2 " << codnum << ' ' << datagen.year() << " D " << _ndoc << " S D";
TExternal_app stampa(str);
stampa.run();
}
}
else
warning_box(TR("Non è stato possibile generare nessun documento"));
//azzera i campi e rimettiti nella condizione iniziale
set(F_NDOC, 0L, 1);
}
//EVADI_TUTTO: metodo che forza a "evaso" tutte le righe e lancia la generazione del buono di consegna associato
void TEvasione_msk::evadi_tutto()
{
TSheet_field& sheet = sfield(F_RIGHE);
const int posevaso = sheet.cid2index(S_EVASO);
FOR_EACH_SHEET_ROW(sheet, r, riga)
{
riga->add("X", posevaso);
sheet.disable_row(r);
}
genera_documento();
}
//SPEZZA_RIGA: metodo che spezza una riga del buono in due righe, una per la quota evasa e una per la quota da evadere
void TEvasione_msk::spezza_riga()
{
TSheet_field& sheet = sfield(F_RIGHE);
FOR_EACH_SHEET_ROW_BACK(sheet, r, riga1)
{
char flgev = riga1->get_char(sheet.cid2index(S_EVASO));
if (flgev != 'X')
{
TToken_string& riga2 = sheet.row(-1);
riga2 = *riga1;
//scrivi le quantità sulla seconda riga
const int dacons2 = riga2.get_int(sheet.cid2index(S_RITIRATO)) - riga2.get_int(sheet.cid2index(S_CONSEGNATO));
riga2.add(dacons2, sheet.cid2index(S_RITIRATO));
riga2.add(dacons2, sheet.cid2index(S_DACONS));
riga2.add(0L, sheet.cid2index(S_CONSEGNATO));
riga2.add(0L, sheet.cid2index(S_PACCHI));
//scrivi le quantità sulla prima riga
const int dacons1 = riga1->get_int(sheet.cid2index(S_RITIRATO)) - riga1->get_int(sheet.cid2index(S_CONSEGNATO));
riga1->add(riga1->get_int(sheet.cid2index(S_CONSEGNATO)), sheet.cid2index(S_RITIRATO));
riga1->add(riga1->get_int(sheet.cid2index(S_CONSEGNATO)), sheet.cid2index(S_DACONS));
riga1->add("X", sheet.cid2index(S_EVASO));
//blocca i campi sulla prima riga
sheet.disable_row(r);
}
}
sheet.sort(sort_by_codart);
sheet.force_update();
}
//SALVA: metodo che salva il buono di prelievo così com'è, senza compiere altre operazioni
void TEvasione_msk::salva()
{
TDoc_key kdoc(get_int(F_ANNO), get(F_CODNUM), get_long(F_NDOC));
TBuono_prelievo doc(kdoc);
TDate datadoc = doc.get_date(DOC_DATADOC);
TLaundry_contract cont(get_long(F_CODCF), get_long(F_CODCONT));
//nel caso avessi spezzato le righe, risrcivendole da capo mi vengono ordinate per codice
//ATTENZIONE: devo eliminare le sole righe che sono sullo sheet, cioè quelle che hanno
//quantità da consegnare maggiore di zero
for (int i = doc.rows(); i > 0; i--)
{
TRiga_documento& row = doc[i];
TBuono_prelievo_row rdoc(row);
if (rdoc.qta_dacons() > 0)
doc.destroy_row(i, true);
}
TSheet_field& sheet = sfield(F_RIGHE);
//riordino lo sheet
sheet.sort(sort_by_codart);
sheet.force_update();
//per ogni riga dello sheet genero una riga documento
FOR_EACH_SHEET_ROW(sheet, r, riga)
{
TRiga_documento& row = doc.new_row("24");
TBuono_prelievo_row rdoc(row);
const char flgev = riga->get(sheet.cid2index(S_EVASO))[0];
bool flag;
if (flgev == 'X')
flag = true;
else
flag = false;
const TString80 codart = riga->get(sheet.cid2index(S_CODART));
rdoc.set_evaso(flag);
rdoc.set_codart(codart);
rdoc.set_desart(riga->get(sheet.cid2index(S_ARTDESCR)));
rdoc.set_causale(riga->get(sheet.cid2index(S_CAUSALE)));
rdoc.set_qta_ritirata(riga->get_int(sheet.cid2index(S_RITIRATO)));
rdoc.set_qta_dacons(riga->get_int(sheet.cid2index(S_DACONS)));
rdoc.set_qta_consegnata(riga->get_int(sheet.cid2index(S_CONSEGNATO)));
rdoc.set_num_pacchi(riga->get_int(sheet.cid2index(S_PACCHI)));
rdoc.set_cong_att(riga->get_int(sheet.cid2index(S_CONGPRE)));
rdoc.set_cong_pre(riga->get_int(sheet.cid2index(S_CONGATT)));
rdoc.set_rifbcon(riga->get(sheet.cid2index(S_RIFBCON)));
//recupero l'unità di misura principale di quest'articolo
TToken_string key;
key.add(codart);
key.add(1);
const TRectype& umart = cache().get(LF_UMART, key);
rdoc.set_um(umart.get(UMART_UM));
//recupero il codiva di quest'articolo
const TRectype& anamag = cache().get(LF_ANAMAG, codart);
rdoc.set_codiva(anamag.get(ANAMAG_CODIVA));
const TRectype& rcont = cont.row(codart);
//controllo da dove devo prendere il prezzo
real prezzo;
if (cont.get_int(LVCONDV_TIPOLIS) == 0)
prezzo = rcont.get_real(LVRCONDV_PREZZO);
else
prezzo = anamag.get_real(ANAMAG_COSTSTD);
rdoc.set_prezzo(prezzo);
//scrivo il magazzino
TString8 magazzino;
TString8 magazzinoc;
magazzino << ini_get_string(CONFIG_DITTA, "lv", "CODMAG") << ini_get_string(CONFIG_DITTA, "lv", "CODMAGN");
magazzinoc << ini_get_string(CONFIG_DITTA, "lv", "CODMAG") << ini_get_string(CONFIG_DITTA, "lv", "CODMAGC");
rdoc.set_mag(magazzino);
rdoc.set_magc(magazzinoc);
}
doc.rewrite();
//se sto evadendo tramite barcode quando salvo salvo anche tutti i pacchi associati
//generando i movimenti di magazzino di scarico
if (_tpev == "B")
{
TLocalisamfile pacchi(LF_PACCHI);
TLocalisamfile movi(LF_MOVMAG);
//cerco l'ultimo numero di chiave in movmag
TISAM_recordset mov("USE MOVMAG");
long nummov = 0;
if(mov.move_last())
nummov += mov.get(MOVMAG_NUMREG).as_int();
const TCausale_magazzino causale((ini_get_string(CONFIG_DITTA, "lv", "CAUSCARMAG")));
TString8 magazzino;
magazzino << ini_get_string(CONFIG_DITTA, "lv", "CODMAG") << ini_get_string(CONFIG_DITTA, "lv", "CODMAGP");
TEsercizi_contabili es;
int annoes = es.date2esc(datadoc);
TMov_mag movmag(++nummov);
movmag.put(MOVMAG_ANNOES, annoes);
movmag.put(MOVMAG_DATAREG, datadoc);
movmag.put(MOVMAG_CODCAUS, causale.codice());
FOR_EACH_ASSOC_OBJECT(_pacchi, o, codpacco, rifdoc)
{
TDoc_key kdoc = *(TToken_string*)rifdoc;
TRiga_pacco rp(codpacco);
const TString80 codart = rp.articolo();
const long qta = rp.quantita().integer();
//recupero l'unità di misura principale di quest'articolo
TToken_string key;
key.add(codart);
key.add(1);
const TString4 um = cache().get(LF_UMART, key, UMART_UM);
rp.set_rigabolla(kdoc.anno(), kdoc.codnum(), kdoc.ndoc(), 0); //SOLUZIONE MOMENTANEA PER VEDERE SE FUNZIONA TUTTO
rp.rewrite(pacchi);
//faccio la nuova riga del movimento di magazzino
TRectype& rmovmag = movmag.new_row();
rmovmag.put(RMOVMAG_CODMAG, magazzino);
rmovmag.put(RMOVMAG_CODART, codart);
rmovmag.put(RMOVMAG_UM, um);
rmovmag.put(RMOVMAG_QUANT, qta);
}
movmag.write(movi);
}
}
//ANNULLA_OPERAZIONI: metodo elimina tutte le quantità scritte durante l'ultima evasione
//e libera i pacchi eventualmente allocati
void TEvasione_msk::annulla_operazioni()
{
//ANNULLA PACCHI
_pacchi.destroy();
//elimino lo sheet senza salvarlo
TSheet_field& sheet = sfield(F_RIGHE);
sheet.destroy();
for(int i = 1; i <= _buonori.rows(); i++)
{
TRiga_documento& row = _buonori[i];
TBuono_prelievo_row rdoc(row);
TToken_string& riga = sheet.row(-1);
riga.add(rdoc.evaso() ? "X" : "", sheet.cid2index(S_EVASO));
riga.add(rdoc.codart(), sheet.cid2index(S_CODART));
riga.add(rdoc.desart(), sheet.cid2index(S_ARTDESCR));
riga.add(rdoc.causale(), sheet.cid2index(S_CAUSALE));
riga.add(rdoc.qta_ritirata(), sheet.cid2index(S_RITIRATO));
riga.add(rdoc.qta_dacons(), sheet.cid2index(S_DACONS));
riga.add(rdoc.qta_consegnata(), sheet.cid2index(S_CONSEGNATO));
const TRectype& anamag = cache().get(LF_ANAMAG, rdoc.codart());
//recupero i dati di interesse dall'anagrafica di magazzino
const long ppconf = anamag.get_long(ANAMAG_PPCONF);
if (ppconf > 0)
riga.add(rdoc.num_pacchi(), sheet.cid2index(S_PACCHI));
else
{
riga.add(0, sheet.cid2index(S_PACCHI));
sheet.disable_cell(i, sheet.cid2index(S_PACCHI));
}
riga.add(rdoc.cong_pre(), sheet.cid2index(S_CONGPRE));
riga.add(rdoc.cong_att(), sheet.cid2index(S_CONGATT));
riga.add(rdoc.rifbcon(), sheet.cid2index(S_RIFBCON));
}
sheet.force_update();
}
//CONTROLLA: metodo che controlla se tutte le righe sono evase
bool TEvasione_msk::controlla()
{
TSheet_field& sheet = sfield(F_RIGHE);
bool evaso = true;
FOR_EACH_SHEET_ROW(sheet, r, row)
{
const char flgev = row->get(sheet.cid2index(S_EVASO))[0];
if (flgev != 'X')
evaso = false;
}
return evaso;
}
//SISTEMA_QUANTITA: metodo che mantiene allineate le quantita consegnate e il numero
//dei pacchi, moltiplicando il numero dei pacchi per i pezzi per pacco; se scrivo una quantità
//a mano ed è prevista una evasione a pacchi, allora aggiorno il numero dei pacchi
void TEvasione_msk::sistema_quantita()
{
TMask& msk = sfield(F_RIGHE).sheet_mask();
TString80 codart = msk.get(S_CODART);
const TRectype& anamag = cache().get(LF_ANAMAG,codart);
//recupero i dati di interesse dall'anagrafica di magazzino
const long ppconf = anamag.get_long(ANAMAG_PPCONF);
if (ppconf > 0)
{
int pacchi = msk.get_int(S_PACCHI);
int qta_consegnata = pacchi * ppconf;
msk.set(S_CONSEGNATO, qta_consegnata);
}
}
void TEvasione_msk::sistema_pacchi()
{
TMask& msk = sfield(F_RIGHE).sheet_mask();
TString80 codart = msk.get(S_CODART);
const TRectype& anamag = cache().get(LF_ANAMAG,codart);
//recupero i dati di interesse dall'anagrafica di magazzino
const long ppconf = anamag.get_long(ANAMAG_PPCONF);
if (ppconf > 0)
{
int qta_consegnata = msk.get_int(S_CONSEGNATO);
int pacchi = qta_consegnata / ppconf;
if (qta_consegnata % ppconf > 0)
pacchi += 1;
msk.set(S_PACCHI, pacchi);
}
}
//EVADI_DA_BARCODE: metodo che somma alla riga corretta un pacco (quello pistolato) e lo assegna a un cliente,
//sottraendolo dal magazzino del pulito
void TEvasione_msk::evadi_da_barcode()
{
TString80 codpacco = get(F_BARCODE);
if (codpacco.full())
{
const TRiga_pacco rp(codpacco);
const TString80 codart = rp.articolo();
const long qtapacco = rp.quantita().integer();
TSheet_field& sheet = sfield(F_RIGHE);
const int pospa = sheet.cid2index(S_PACCHI);
const int posco = sheet.cid2index(S_CONSEGNATO);
//se il pacco è già stato pistolettato lo tolgo dai pacchi da evadere, altrimenti cerco di sommarlo
//a una riga documento esistente
if (_pacchi.is_key(codpacco))
{
_pacchi.remove(codpacco);
FOR_EACH_SHEET_ROW(sheet, r, riga)
{
const TString80 scodart = riga->get(sheet.cid2index(S_CODART));
const char sevaso = riga->get_char(sheet.cid2index(S_EVASO));
if (scodart == codart)
{
if (yesno_box(TR("ATTENZIONE: il pacco risulta già conteggato; si desidera annularlo?")))
{
int qtadacon = riga->get_int(sheet.cid2index(S_DACONS));
int pacchi = riga->get_int(pospa); pacchi -= 1;
int qtacon = riga->get_int(posco); qtacon -= qtapacco;
riga->add(pacchi, pospa);
riga->add(qtacon, posco);
if(qtacon < qtadacon && sevaso == 'X')
{
riga->add("", sheet.cid2index(S_EVASO));
sheet.enable_row(r);
}
break;
}
else
break;
}
}
}
else
{
TDoc_key kdoc(get_int(F_ANNO), get(F_CODNUM), get_int(F_NDOC));
bool trovato = false;
//cerco la prima riga non evasa di quell'articolo
FOR_EACH_SHEET_ROW(sheet, r, riga)
{
const TString80 scodart = riga->get(sheet.cid2index(S_CODART));
if (scodart == codart)
trovato = true;
}
if(trovato)
{
trovato = false;
FOR_EACH_SHEET_ROW(sheet, r, riga)
{
const TString80 scodart = riga->get(sheet.cid2index(S_CODART));
const char sevaso = riga->get_char(sheet.cid2index(S_EVASO));
if (scodart == codart && sevaso != 'X')
{
int qtadacon = riga->get_int(sheet.cid2index(S_DACONS));
int pacchi = riga->get_int(pospa); pacchi += 1;
int qtacon = riga->get_int(posco); qtacon += qtapacco;
riga->add(pacchi, pospa);
riga->add(qtacon, posco);
if (qtacon > qtadacon)
{
warning_box(TR("ATTENZIONE: si sta consegnando un quantitativo maggiore al dovuto"));
riga->add('X', sheet.cid2index(S_EVASO));
}
if (qtacon == qtadacon)
riga->add('X', sheet.cid2index(S_EVASO));
trovato = true;
_pacchi.add(codpacco, kdoc);
}
}
if (!trovato)
{
if(yesno_box(TR("Si desidera provare a sommare il pacco a una riga già evasa?")))
{
FOR_EACH_SHEET_ROW(sheet, r, riga)
{
const TString80 scodart = riga->get(sheet.cid2index(S_CODART));
if (scodart == codart)
{
int pacchi = riga->get_int(pospa); pacchi += 1;
int qtacon = riga->get_int(posco); qtacon += qtapacco;
riga->add(pacchi, pospa);
riga->add(qtacon, posco);
trovato = true;
_pacchi.add(codpacco, kdoc);
}
}
}
}
if (!trovato)
warning_box(TR("Non è stato possibile sommare il pacco a nessuna riga del buono"));
}
}
}
}
void TEvasione_msk:: on_idle()
{
TMask::on_idle();
if (_autoselect >= 0 && get(F_BARCODE).full())
{
reset(F_BARCODE);
field(F_BARCODE).set_focus();
_autoselect = -1;
}
}
//ON_FIELD_EVENT: metodo che gestisce gli eventi sui campi della maschera
bool TEvasione_msk::on_field_event(TOperable_field& f, TField_event e, long jolly)
{
//a seconda del bottone premuto esegui un metodo diverso
switch (f.dlg())
{
case DLG_SELECT:
{
if (e == fe_button)
evadi_tutto();
}
break;
case DLG_PREVIEW:
{
riordina_righe();
}
break;
case DLG_ELABORA:
{
if (e == fe_button)
if (controlla())
genera_documento();
else
{
if(yesno_box(TR("ATTENZIONE: non tutte le righe sono evase. Si desidera continuare ugualmente?")))
{
if(yesno_box(TR("Si desidera considerare evase tutte le righe?"
"(in caso contrario le righe evase parzialmente verranno spezzate su due righe)")))
evadi_tutto();
else
{
spezza_riga();
genera_documento();
}
}
else
riordina_righe();
}
}
break;
case DLG_SAVEREC:
{
if (e == fe_button)
salva();
}
break;
case DLG_CANCEL:
{
if (e == fe_button && jolly == 0)
{
annulla_operazioni();
return false;
}
}
break;
case F_NDOC:
{
if (e == fe_modify)
if (f.get_long() > 0)
carica_righe();
else
{
sfield(F_RIGHE).destroy();
disable(DLG_SELECT);
disable(DLG_PREVIEW);
disable(DLG_ELABORA);
disable(DLG_SAVEREC);
disable(DLG_CANCEL);
reset(F_STATO);
reset(F_DATADOC); setta_campi_data();
reset(F_CODCF); setta_campi_cliente();
hide(F_RIGHE);
}
}
break;
case F_DATADOC:
{
if (e == fe_modify)
setta_campi_data();
}
break;
case F_CODCF:
{
if (e == fe_modify)
setta_campi_cliente();
}
break;
case F_BARCODE:
{
if (e == fe_modify && f.get().full())
{
_autoselect = 1;
evadi_da_barcode();
sfield(F_RIGHE).force_update();
if (controlla())
send_key(K_SPACE, DLG_ELABORA);
}
}
break;
case S_CONSEGNATO:
{
if (e == fe_modify)
{
TSheet_field& sheet = sfield(F_RIGHE);
TMask& msk = sheet.sheet_mask();
//la riga risulta evasa se la quantità consegnata è maggiore o uguale alla quantità da consegnare
if(msk.get_long(S_CONSEGNATO) > msk.get_long(S_DACONS))
{
warning_box(TR("ATTENZIONE: si sta consegnando un quantitativo maggiore al dovuto"));
msk.set(S_EVASO, "X");
TToken_string& riga = sheet.row(sheet.selected());
riga.add("X", sheet.cid2index(S_EVASO));
sheet.disable_row(sheet.selected());
}
else if (msk.get_long(S_CONSEGNATO) == msk.get_long(S_DACONS))
{
msk.set(S_EVASO, "X");
TToken_string& riga = sheet.row(sheet.selected());
riga.add("X", sheet.cid2index(S_EVASO));
sheet.disable_row(sheet.selected());
}
sistema_pacchi();
if (controlla())
send_key(K_SPACE, DLG_ELABORA, &f);
}
}
break;
case S_PACCHI:
{
if (e == fe_modify)
sistema_quantita();
}
break;
default:break;
}
return true;
}
//metodo costruttore che precarica i campi di interesse sulla maschera
TEvasione_msk::TEvasione_msk():TAutomask("lv3200a")
{
//precarico i campi fissi
set(F_CODNUM, ini_get_string(CONFIG_DITTA, "lv", "NUM_PRE", NULL, 0));
set(F_TPDOC, ini_get_string(CONFIG_DITTA, "lv", "TIPODOC_PRE", NULL, 0));
const TRectype& tpdoc = cache().get("%NUM", ini_get_string(CONFIG_DITTA, "lv", "TIPODOC_PRE", NULL, 0));
set(F_DESCR, tpdoc.get("S0"));
TDate data(TODAY);
TEsercizi_contabili es;
int annoes = es.date2esc(data);
set(F_ANNO, annoes);
_tpev = main_app().argv(2);
if (_tpev == "B")
{
_autoselect = 1;
show(F_BARCODE);
}
else
{
_autoselect = -1;
hide(F_BARCODE);
}
hide(F_RIGHE);
disable(DLG_SELECT);
disable(DLG_PREVIEW);
disable(DLG_ELABORA);
disable(DLG_SAVEREC);
disable(DLG_CANCEL);
_ndoc = 0;
}
/////////////////////////////
//// TEVASIONE_APP ////
/////////////////////////////
//classe TEvasione_app
class TEvasione_app : public TSkeleton_application
{
TEvasione_msk* _msk;
protected:
virtual bool create();
virtual bool destroy();
public:
bool transfer();
virtual void main_loop();
};
//CREATE: metodo costruttore
bool TEvasione_app::create()
{
_msk = new TEvasione_msk;
open_files(LF_DOC, LF_RIGHEDOC);
return TSkeleton_application::create();
}
//DESTROY: metodo distruttore
bool TEvasione_app::destroy()
{
delete _msk;
return TApplication::destroy();
}
//TRANSFER: metodo che scorre i campi nome e, se sono pieni, richiama il metodo
//ELABORA_FILE(), che effettivamente fa l'elaborazione
bool TEvasione_app::transfer()
{
return true;
}
void TEvasione_app::main_loop()
{
while (_msk->run() == K_ENTER)
transfer();
}
int lv3200(int argc, char *argv[])
{
TEvasione_app a;
a.run (argc, argv, "Evasione Buoni di Prelievo");
return TRUE;
}