Oggettivazione Contabilizzazione e Generazione effetti.
velib04a -> Fatturazione bolle velib04b -> Contabilizzazione documenti velib04c -> Generazione effetti git-svn-id: svn://10.65.10.50/trunk@5043 c028cbd2-c16b-5b4b-a496-9718f37d4682
This commit is contained in:
parent
a5af19ddf9
commit
4a8a95de8f
174
ve/velib.h
174
ve/velib.h
@ -673,7 +673,7 @@ public:
|
|||||||
virtual ~TConsegna_ordini() { }
|
virtual ~TConsegna_ordini() { }
|
||||||
};
|
};
|
||||||
|
|
||||||
class TFatturazione_bolle : public TElaborazione // velib04
|
class TFatturazione_bolle : public TElaborazione // velib04a
|
||||||
{
|
{
|
||||||
TToken_string _cod_desc;
|
TToken_string _cod_desc;
|
||||||
|
|
||||||
@ -690,15 +690,130 @@ public:
|
|||||||
virtual ~TFatturazione_bolle() { }
|
virtual ~TFatturazione_bolle() { }
|
||||||
};
|
};
|
||||||
|
|
||||||
class TContabilizzazione : public TElaborazione // velib04
|
// Tipi di errore validi solo per TContabilizzazione e TGenerazione_effetti
|
||||||
|
|
||||||
|
enum error_type {
|
||||||
|
no_error,
|
||||||
|
nr_es_error,
|
||||||
|
nr_reg_error,
|
||||||
|
nr_doc_error,
|
||||||
|
chg_stat_error,
|
||||||
|
clifo_error,
|
||||||
|
ultprot_error,
|
||||||
|
datadoc_error,
|
||||||
|
caus_error,
|
||||||
|
register_error,
|
||||||
|
change_error,
|
||||||
|
val_error,
|
||||||
|
codpag_error,
|
||||||
|
row_type_error,
|
||||||
|
no_rows_error,
|
||||||
|
conto_error,
|
||||||
|
movement_error,
|
||||||
|
write_error,
|
||||||
|
scadenze_error,
|
||||||
|
generic_error
|
||||||
|
};
|
||||||
|
|
||||||
|
class TBill;
|
||||||
|
|
||||||
|
class TContabilizzazione : public TElaborazione // velib04b
|
||||||
{
|
{
|
||||||
|
bool _auto_data; // Flag per data di registrazione automatica
|
||||||
|
byte _nump_iva; // se 1 prende il numero protocollo da registro iva, se 2 prende il numero protocollo dal numero doc.
|
||||||
|
TDate _data_reg; // Data di registrazione documenti
|
||||||
|
long _total_docs;// Numero di documenti contabilizzati
|
||||||
|
error_type _error; // Errore rilevato durante l'elaborazione
|
||||||
|
bool _can_write; // se TRUE e' abilitata la scrittura. Non appena rileva un errore rimane a FALSE for this instance
|
||||||
|
TString16 _spin_cod, // codice iva spese d'incasso
|
||||||
|
_spbo_cod; // codice iva spese bolli
|
||||||
|
TAssoc_array _righe_iva; // array per la memorizzazione delle righe iva raggruppate in codesto modo:
|
||||||
|
// CODICE_IVA+TIPOCF+GRUPPO+CONTO+SOTTOCONTO
|
||||||
|
// una volta completo, tale array viene scorso per comporre le righe IVA
|
||||||
|
// del movimento
|
||||||
|
|
||||||
|
// Files, tabelle, oggetti contabili ed altre amenita'...
|
||||||
|
TLocalisamfile *_anamag, // file delle anagrafiche di magazzino
|
||||||
|
*_fcaus,
|
||||||
|
*_frcaus,
|
||||||
|
*_attiv,
|
||||||
|
*_part,
|
||||||
|
*_scad,
|
||||||
|
*_pags,
|
||||||
|
*_occas,
|
||||||
|
*_docfile,
|
||||||
|
*_rdocfile;
|
||||||
|
|
||||||
|
TTable *_cpg, // tabella condizioni di pagamento
|
||||||
|
*_gmc, // tabella gruppi/sottogruppi merceologici
|
||||||
|
*_rfa, // tabella raggruppamenti fiscali
|
||||||
|
*_cve, // tabella categorie di vendita
|
||||||
|
*_val, // tabella valute estere
|
||||||
|
*_tri, // tabella tipi di riga
|
||||||
|
*_prs, // tabella prestazioni
|
||||||
|
*_spp, // tabella spese
|
||||||
|
*_caa, // tabella categorie acquisto articoli
|
||||||
|
*_cra, // tabella categorie ricavo articoli
|
||||||
|
*_cco; // tabella categorie contabili
|
||||||
|
TRelation *_clifo; // relazione dei clienti e fornitori + cfven
|
||||||
|
|
||||||
|
// Parametri da leggere all'inizio dell'elaborazione tramite load_parameters()
|
||||||
|
bool _nump_cfg; // se TRUE prende il numero rif. partita dal numero protocollo
|
||||||
|
bool _sc_enabled;// se TRUE il saldaconto di ditta e' abilitato
|
||||||
|
TToken_string _search_seq; // Sequenza di ricerca del conto costo/ricavo la correttezza dell'ordinamento
|
||||||
|
// va controllata nel programma di modifica parametri:
|
||||||
|
// "" = fine ordinamento
|
||||||
|
// CF = cliente fornitore
|
||||||
|
// CA = causale
|
||||||
|
// AR = articolo (costo/ricavo)
|
||||||
|
// GM = gruppo merceologico
|
||||||
|
// SM = sottogruppo merceologico
|
||||||
|
// RF = raggruppamento fiscale
|
||||||
|
// CV = categoria di vendita
|
||||||
|
// CC = categoria contabile
|
||||||
|
// Gli utlimi 6 fanno parte della ricerca per costi ricavi, in particolare AR,GM,SM e RF
|
||||||
|
// non possono essere interrotti da CV o CC. Ad es. CA|CF|AR|CV|GM|CC|RF non e' valida come stringa
|
||||||
|
// di ricerca.
|
||||||
|
protected:
|
||||||
|
// Carica i parametri dalla configurazione
|
||||||
|
bool load_parameters();
|
||||||
|
// Compila la testata del movimento
|
||||||
|
error_type compile_head_mov(TDocumento&);
|
||||||
|
// Funzione per ricercare il conto di costo/ricavo
|
||||||
|
error_type search_costo_ricavo(TBill&, const TRiga_documento&);
|
||||||
|
// Funzione per aggiungere la riga iva al TAssoc_array _righe_iva
|
||||||
|
error_type add_iva_row(const TBill&, const TRiga_documento&);
|
||||||
|
// Funzione atomica per aggiungere le righe di spese d'incasso e bolli al TAssoc_array _righe_iva
|
||||||
|
void calculate_spese(real&, real&, int, bool, bool);
|
||||||
|
// Funzione per aggiungere le righe di spese d'incasso e bolli al TAssoc_array _righe_iva (chiama calculate_spese())
|
||||||
|
error_type add_spese_inbo(TDocumento&);
|
||||||
|
// Crea le righe iva sul movimento
|
||||||
|
error_type create_iva_rows(TDocumento&);
|
||||||
|
// Crea la riga di totale documento
|
||||||
|
error_type create_total_doc_row();
|
||||||
|
// Compila le righe del movimento
|
||||||
|
error_type compile_rows_mov(TDocumento&);
|
||||||
|
// scrive le scadenze
|
||||||
|
error_type write_scadenze(TDocumento&);
|
||||||
|
// scrive il movimento e le scadenze
|
||||||
|
error_type write_all(TDocumento&);
|
||||||
|
// Cambia lo stato del documento
|
||||||
|
error_type change_doc_status(TDocumento&);
|
||||||
|
// Visualizza l'ultimo errore rilevato
|
||||||
|
void display_error(TDocumento&);
|
||||||
|
// Verifica se non ci sono stati errori
|
||||||
|
bool good() const { return _error == no_error;}
|
||||||
|
// Ritorna TRUE se il saldaconto e' abilitato (verifica anche la causale del documento corrente)
|
||||||
|
bool sc_enabled() const ;
|
||||||
public:
|
public:
|
||||||
virtual bool elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
virtual bool elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
||||||
const TDate& data_elab);
|
const TDate& data_elab);
|
||||||
|
void set_auto(const bool a) { _auto_data = a; }
|
||||||
|
void set_nump(const byte n) { _nump_iva = n; }
|
||||||
|
const long docs() { return _total_docs; }
|
||||||
TContabilizzazione(const char* cod);
|
TContabilizzazione(const char* cod);
|
||||||
TContabilizzazione(const TRectype& rec) : TElaborazione(rec) { }
|
TContabilizzazione(const TRectype& rec);
|
||||||
virtual ~TContabilizzazione() { }
|
virtual ~TContabilizzazione();
|
||||||
};
|
};
|
||||||
|
|
||||||
class TCopia_documento : public TElaborazione // velib04
|
class TCopia_documento : public TElaborazione // velib04
|
||||||
@ -713,15 +828,56 @@ public:
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
class TGenerazione_effetti : public TElaborazione // velib04
|
class TGenerazione_effetti : public TElaborazione // velib04c
|
||||||
{
|
{
|
||||||
|
error_type _error; // Errore rilevato durante l'elaborazione
|
||||||
|
long _total_bills; // Totale effetti generati
|
||||||
|
bool _can_write; // se TRUE e' abilitata la scrittura. Non appena rileva un errore rimane a FALSE for this instance
|
||||||
|
TBit_array _valid_array; // array dei tipi di pagamento validi per la generazione di effetti
|
||||||
|
|
||||||
|
TLocalisamfile *_efffile, // file effetti
|
||||||
|
*_refffile, // file righe di effetti
|
||||||
|
*_cessfile,
|
||||||
|
*_docfile,
|
||||||
|
*_rdocfile,
|
||||||
|
*_clifo,
|
||||||
|
*_cfven,
|
||||||
|
*_tab,
|
||||||
|
*_occas;
|
||||||
|
TTable *_cpg; // tabella condizioni di pagamento
|
||||||
|
TArray _effetti_array;//Array di effetti (TEffetto) da scrivere
|
||||||
|
TAssoc_array _group_array; // Assoc_array dei documenti da raggruppare. La chiave di ogni elemento
|
||||||
|
// e composta dagli stessi criteri di raggruppamento (vedi sotto)
|
||||||
|
// Ogni elemento e una TToken_string. Ogni elemento della TToken_string contiene
|
||||||
|
// la chiave per identificare il documento che fa parte di quel raggruppamento
|
||||||
|
protected:
|
||||||
|
// Visualizza l'ultimo errore rilevato
|
||||||
|
void display_error(TDocumento& doc);
|
||||||
|
// Restituisce TRUE se il tipo di pagamento passato e' valido per generare l'effetto
|
||||||
|
bool valid_type(int) const ;
|
||||||
|
// Genera l'effetto
|
||||||
|
void generate_bill(TDocumento&);
|
||||||
|
// Effettua il raggruppamento vero e proprio degli effetti (solo se ci sono elementi nell'assoc_array
|
||||||
|
void group_bills(TDocumento&);
|
||||||
|
// Istanzia il pagamento corrente
|
||||||
|
void calc_pagamento(TDocumento&, TString16&, TString16&);
|
||||||
|
// Scrive i record array degli effetti raggruppati
|
||||||
|
error_type write_groups();
|
||||||
|
// Cambia lo stato dei gruppi di documenti raggruppati in effetti
|
||||||
|
error_type change_group_status(TDocumento&);
|
||||||
|
// Cambia lo stato del documento
|
||||||
|
error_type change_doc_status(TDocumento&);
|
||||||
|
// Verifica se non ci sono stati errori
|
||||||
|
bool good() const { return _error == no_error;}
|
||||||
public:
|
public:
|
||||||
virtual bool elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
virtual bool elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
||||||
const TDate& data_elab);
|
const TDate& data_elab);
|
||||||
|
|
||||||
|
const long bills() { return _total_bills; }
|
||||||
|
void set_group(TAssoc_array& a) { _group_array = a; }
|
||||||
TGenerazione_effetti(const char* cod);
|
TGenerazione_effetti(const char* cod);
|
||||||
TGenerazione_effetti(const TRectype& rec) : TElaborazione(rec) { }
|
TGenerazione_effetti(const TRectype& rec);
|
||||||
virtual ~TGenerazione_effetti() { }
|
virtual ~TGenerazione_effetti();
|
||||||
};
|
};
|
||||||
|
|
||||||
class TLista_elaborazioni : public TObject // velib04
|
class TLista_elaborazioni : public TObject // velib04
|
||||||
|
237
ve/velib04.cpp
237
ve/velib04.cpp
@ -401,225 +401,6 @@ bool TConsegna_ordini::elabora(TLista_documenti& doc_in, TLista_documenti& doc_o
|
|||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
// TFatturazione bolle
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
TFatturazione_bolle::TFatturazione_bolle(const char* cod)
|
|
||||||
: TElaborazione(cod)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void TFatturazione_bolle::tipi_validi(TToken_string& tipi) const
|
|
||||||
{
|
|
||||||
const TString& s2 = get("S2");
|
|
||||||
tipi.cut(0);
|
|
||||||
TString16 t;
|
|
||||||
for (int i = 0; i < 5; i++)
|
|
||||||
{
|
|
||||||
t = s2.mid(i*4, 4);
|
|
||||||
t.trim();
|
|
||||||
if (t.not_empty())
|
|
||||||
tipi.add(t);
|
|
||||||
}
|
|
||||||
CHECK(!tipi.empty_items(), "Nessun tipo documento valido");
|
|
||||||
}
|
|
||||||
|
|
||||||
void TFatturazione_bolle::stati_validi(TToken_string& stati) const
|
|
||||||
{
|
|
||||||
const TString& s7 = get("S7");
|
|
||||||
stati.cut(0);
|
|
||||||
TString16 s;
|
|
||||||
for (int i = 0; i < 5; i++)
|
|
||||||
{
|
|
||||||
s = s7.mid(i*4, 1);
|
|
||||||
s.trim();
|
|
||||||
if (s.not_empty())
|
|
||||||
stati.add(s);
|
|
||||||
}
|
|
||||||
CHECK(!stati.empty_items(), "Nessuno stato documento valido");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool TFatturazione_bolle::raggruppa(TDocumento& doc_in, TDocumento& doc_out)
|
|
||||||
{
|
|
||||||
#ifdef DBG
|
|
||||||
const TString tipi = get("S2");
|
|
||||||
const TString& tipodoc = doc_in.tipo().codice();
|
|
||||||
for (int i = 0; i < 5; i++)
|
|
||||||
{
|
|
||||||
if (tipodoc == tipi.mid(i*4, 4))
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (i >= 5)
|
|
||||||
{
|
|
||||||
NFCHECK("Tipo documento non valido: '%s'", (const char*)tipodoc);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
const char stato_finale_in = get_char("S4");
|
|
||||||
doc_in.stato(stato_finale_in);
|
|
||||||
|
|
||||||
const TString& tipo_out = get("S8");
|
|
||||||
doc_out.put("TIPODOC", tipo_out);
|
|
||||||
|
|
||||||
const char stato_finale_out = get_char("S9");
|
|
||||||
doc_out.stato(stato_finale_out);
|
|
||||||
|
|
||||||
if (gestione_riferimenti())
|
|
||||||
{
|
|
||||||
// Determina ed eventualmente crea la riga di riferimento
|
|
||||||
const int riga_rif = riferimenti_in_testa() ? 1 : doc_out.rows()+1;
|
|
||||||
if (riga_rif > doc_out.rows())
|
|
||||||
{
|
|
||||||
TRiga_documento& rout = doc_out.new_row();
|
|
||||||
rout.forza_sola_descrizione();
|
|
||||||
}
|
|
||||||
|
|
||||||
TRiga_documento& rout = doc_out[riga_rif];
|
|
||||||
|
|
||||||
// Costruisce la stringa di riferimento
|
|
||||||
TString riferimento(80);
|
|
||||||
riferimento = doc_in.tipo().riferimento();
|
|
||||||
if (riferimento.empty())
|
|
||||||
riferimento = doc_in.tipo().descrizione();
|
|
||||||
riferimento << " n. " << doc_in.numero();
|
|
||||||
riferimento << " del " << doc_in.data().string();
|
|
||||||
|
|
||||||
// Setta la descrizione se vuota
|
|
||||||
if (rout.get("DESCR").empty())
|
|
||||||
rout.put("DESCR", riferimento);
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// Altrimenti aggiungi il riferimento al memo
|
|
||||||
TString memo(1024);
|
|
||||||
memo = rout.get("DESCEST");
|
|
||||||
if (memo.empty())
|
|
||||||
rout.put("DESCLUNGA", "X");
|
|
||||||
else
|
|
||||||
memo << '\n';
|
|
||||||
memo << riferimento;
|
|
||||||
rout.put("DESCEST", memo);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const bool ignora_desc = ignora_descrizioni();
|
|
||||||
|
|
||||||
TToken_string campi_riga(80);
|
|
||||||
const bool ragg_rig = raggruppa_righe();
|
|
||||||
if (ragg_rig)
|
|
||||||
{
|
|
||||||
campi_riga = "CODART|UMQTA"; // Uguali sempre
|
|
||||||
// Uguali opzionalmente
|
|
||||||
if (riga_uguale(0)) campi_riga.add("CODMAG");
|
|
||||||
if (riga_uguale(1)) campi_riga.add("CODIVA");
|
|
||||||
if (riga_uguale(2)) campi_riga.add("PREZZO|SCONTO");
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int r = 1; r <= doc_in.rows(); r++)
|
|
||||||
{
|
|
||||||
const TRiga_documento& rin = doc_in[r];
|
|
||||||
const bool rindesc = rin.sola_descrizione(); // La riga di input e' descrittiva
|
|
||||||
if (ignora_desc && rindesc)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
bool elaborata = FALSE;
|
|
||||||
|
|
||||||
// Raggruppo le righe se e' settato il falg di raggruppamento e
|
|
||||||
// se la riga non contiene solo una descrizione
|
|
||||||
if (ragg_rig && !rindesc) // Se devo raggruppare le righe ...
|
|
||||||
{
|
|
||||||
const int last = doc_out.rows();
|
|
||||||
for (int o = 1; o <= last; o++) // ... cerca una riga compatibile
|
|
||||||
{
|
|
||||||
TRiga_documento& rout = doc_out[o];
|
|
||||||
if (rout.sola_descrizione()) // Ignora le righe descrittive
|
|
||||||
continue;
|
|
||||||
if (rin.raggruppabile(rout, campi_riga)) // Se esiste una riga compatibile ...
|
|
||||||
{
|
|
||||||
rout += rin; // ... sommaci la quantita' ecc.
|
|
||||||
elaborata = TRUE; // Ricorda di averla gia' elaborata
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!elaborata) // Se la riga non e' stata gia' sommata ...
|
|
||||||
{
|
|
||||||
TRiga_documento& rout = doc_out.new_row(); // ... crea una riga nuova e ...
|
|
||||||
doc_out.copy_data(rout, rin); // ... copiaci tutti i campi della riga sorgente.
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool TFatturazione_bolle::elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
|
||||||
const TDate& data_elab)
|
|
||||||
{
|
|
||||||
bool ok = TRUE;
|
|
||||||
|
|
||||||
TToken_string campi_doc(128); // Lista di campi che devono essere uguali
|
|
||||||
campi_doc = "TIPOCF|CODCF|CODVAL|CODLIN"; // Uguali sempre
|
|
||||||
|
|
||||||
// Uguali opzionalmente
|
|
||||||
const char* cond[] = { "CAMBIO", "SCONTO", "TIPODOC", "CODNUM",
|
|
||||||
"CODPAG", "CODABIA|CODCABA", "CODLIST", "CODAG",
|
|
||||||
"CODSPMEZZO", "CODPORTO", "CAUSTRASP", "CODVETT1|CODVETT2|CODVETT3",
|
|
||||||
NULL };
|
|
||||||
for (int u = 0; cond[u]; u++)
|
|
||||||
if (doc_uguale(u)) campi_doc.add(cond[u]);
|
|
||||||
|
|
||||||
for (int id = 0; id < doc_in.items() && ok; id++)
|
|
||||||
{
|
|
||||||
TDocumento& campione = doc_in[id];
|
|
||||||
const int tot = doc_out.items();
|
|
||||||
int od = tot;
|
|
||||||
|
|
||||||
if (campione.raggruppabile()) // Se il documento ha il flag di raggruppabilita' ...
|
|
||||||
{
|
|
||||||
for (od = 0; od < tot; od++) // ... cerca un documento compatibile.
|
|
||||||
{
|
|
||||||
if (campione.raggruppabile(doc_out[od], campi_doc))
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (od >= tot) // Se non ho trovato un documento compatibile ...
|
|
||||||
{ // ... creane uno nuovo (certamente compatibile)
|
|
||||||
const char provv = tipo_numerazione();
|
|
||||||
const int anno = campione.anno();
|
|
||||||
const TString codnum = codice_numerazione_finale();
|
|
||||||
TDocumento* new_doc = new TDocumento(provv, anno, codnum, -1);
|
|
||||||
// Copia i dati della testata
|
|
||||||
TDocumento::copy_data(new_doc->head(), campione.head());
|
|
||||||
|
|
||||||
new_doc->put("DATADOC", data_elab);
|
|
||||||
|
|
||||||
// Aggiungilo alla lista dei documenti in uscita
|
|
||||||
od = doc_out.add(new_doc);
|
|
||||||
}
|
|
||||||
|
|
||||||
ok = raggruppa(campione, doc_out[od]);
|
|
||||||
}
|
|
||||||
return ok;
|
|
||||||
}
|
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
// TContabilizzazione
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
TContabilizzazione::TContabilizzazione(const char* cod)
|
|
||||||
: TElaborazione(cod)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
bool TContabilizzazione::elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
|
||||||
const TDate& data_elab)
|
|
||||||
{
|
|
||||||
CHECK(doc_in.items() == 1, "Si deve specificare uno e un solo documento in entrata");
|
|
||||||
CHECK(doc_out.items() == 1, "Si deve specificare uno e un solo documento in uscita");
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
// TCopia_documento
|
// TCopia_documento
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
@ -641,24 +422,6 @@ bool TCopia_documento::elabora(TLista_documenti& doc_in, TLista_documenti& doc_o
|
|||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
// TGenerazione_effetti
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
TGenerazione_effetti::TGenerazione_effetti(const char* cod)
|
|
||||||
: TElaborazione(cod)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
bool TGenerazione_effetti::elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
|
||||||
const TDate& data_elab)
|
|
||||||
{
|
|
||||||
CHECK(doc_in.items() == 1, "Si deve specificare uno e un solo documento in entrata");
|
|
||||||
CHECK(doc_out.items() == 1, "Si deve specificare uno e un solo documento in uscita");
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
// TLista_elaborazioni
|
// TLista_elaborazioni
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
|
205
ve/velib04a.cpp
Executable file
205
ve/velib04a.cpp
Executable file
@ -0,0 +1,205 @@
|
|||||||
|
#include "velib.h"
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////
|
||||||
|
// TFatturazione bolle
|
||||||
|
///////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
TFatturazione_bolle::TFatturazione_bolle(const char* cod)
|
||||||
|
: TElaborazione(cod)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void TFatturazione_bolle::tipi_validi(TToken_string& tipi) const
|
||||||
|
{
|
||||||
|
const TString& s2 = get("S2");
|
||||||
|
tipi.cut(0);
|
||||||
|
TString16 t;
|
||||||
|
for (int i = 0; i < 5; i++)
|
||||||
|
{
|
||||||
|
t = s2.mid(i*4, 4);
|
||||||
|
t.trim();
|
||||||
|
if (t.not_empty())
|
||||||
|
tipi.add(t);
|
||||||
|
}
|
||||||
|
CHECK(!tipi.empty_items(), "Nessun tipo documento valido");
|
||||||
|
}
|
||||||
|
|
||||||
|
void TFatturazione_bolle::stati_validi(TToken_string& stati) const
|
||||||
|
{
|
||||||
|
const TString& s7 = get("S7");
|
||||||
|
stati.cut(0);
|
||||||
|
TString16 s;
|
||||||
|
for (int i = 0; i < 5; i++)
|
||||||
|
{
|
||||||
|
s = s7.mid(i*4, 1);
|
||||||
|
s.trim();
|
||||||
|
if (s.not_empty())
|
||||||
|
stati.add(s);
|
||||||
|
}
|
||||||
|
CHECK(!stati.empty_items(), "Nessuno stato documento valido");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool TFatturazione_bolle::raggruppa(TDocumento& doc_in, TDocumento& doc_out)
|
||||||
|
{
|
||||||
|
#ifdef DBG
|
||||||
|
const TString tipi = get("S2");
|
||||||
|
const TString& tipodoc = doc_in.tipo().codice();
|
||||||
|
for (int i = 0; i < 5; i++)
|
||||||
|
{
|
||||||
|
if (tipodoc == tipi.mid(i*4, 4))
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (i >= 5)
|
||||||
|
{
|
||||||
|
NFCHECK("Tipo documento non valido: '%s'", (const char*)tipodoc);
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
const char stato_finale_in = get_char("S4");
|
||||||
|
doc_in.stato(stato_finale_in);
|
||||||
|
|
||||||
|
const TString& tipo_out = get("S8");
|
||||||
|
doc_out.put("TIPODOC", tipo_out);
|
||||||
|
|
||||||
|
const char stato_finale_out = get_char("S9");
|
||||||
|
doc_out.stato(stato_finale_out);
|
||||||
|
|
||||||
|
if (gestione_riferimenti())
|
||||||
|
{
|
||||||
|
// Determina ed eventualmente crea la riga di riferimento
|
||||||
|
const int riga_rif = riferimenti_in_testa() ? 1 : doc_out.rows()+1;
|
||||||
|
if (riga_rif > doc_out.rows())
|
||||||
|
{
|
||||||
|
TRiga_documento& rout = doc_out.new_row();
|
||||||
|
rout.forza_sola_descrizione();
|
||||||
|
}
|
||||||
|
|
||||||
|
TRiga_documento& rout = doc_out[riga_rif];
|
||||||
|
|
||||||
|
// Costruisce la stringa di riferimento
|
||||||
|
TString riferimento(80);
|
||||||
|
riferimento = doc_in.tipo().riferimento();
|
||||||
|
if (riferimento.empty())
|
||||||
|
riferimento = doc_in.tipo().descrizione();
|
||||||
|
riferimento << " n. " << doc_in.numero();
|
||||||
|
riferimento << " del " << doc_in.data().string();
|
||||||
|
|
||||||
|
// Setta la descrizione se vuota
|
||||||
|
if (rout.get("DESCR").empty())
|
||||||
|
rout.put("DESCR", riferimento);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Altrimenti aggiungi il riferimento al memo
|
||||||
|
TString memo(1024);
|
||||||
|
memo = rout.get("DESCEST");
|
||||||
|
if (memo.empty())
|
||||||
|
rout.put("DESCLUNGA", "X");
|
||||||
|
else
|
||||||
|
memo << '\n';
|
||||||
|
memo << riferimento;
|
||||||
|
rout.put("DESCEST", memo);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const bool ignora_desc = ignora_descrizioni();
|
||||||
|
|
||||||
|
TToken_string campi_riga(80);
|
||||||
|
const bool ragg_rig = raggruppa_righe();
|
||||||
|
if (ragg_rig)
|
||||||
|
{
|
||||||
|
campi_riga = "CODART|UMQTA"; // Uguali sempre
|
||||||
|
// Uguali opzionalmente
|
||||||
|
if (riga_uguale(0)) campi_riga.add("CODMAG");
|
||||||
|
if (riga_uguale(1)) campi_riga.add("CODIVA");
|
||||||
|
if (riga_uguale(2)) campi_riga.add("PREZZO|SCONTO");
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int r = 1; r <= doc_in.rows(); r++)
|
||||||
|
{
|
||||||
|
const TRiga_documento& rin = doc_in[r];
|
||||||
|
const bool rindesc = rin.sola_descrizione(); // La riga di input e' descrittiva
|
||||||
|
if (ignora_desc && rindesc)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
bool elaborata = FALSE;
|
||||||
|
|
||||||
|
// Raggruppo le righe se e' settato il falg di raggruppamento e
|
||||||
|
// se la riga non contiene solo una descrizione
|
||||||
|
if (ragg_rig && !rindesc) // Se devo raggruppare le righe ...
|
||||||
|
{
|
||||||
|
const int last = doc_out.rows();
|
||||||
|
for (int o = 1; o <= last; o++) // ... cerca una riga compatibile
|
||||||
|
{
|
||||||
|
TRiga_documento& rout = doc_out[o];
|
||||||
|
if (rout.sola_descrizione()) // Ignora le righe descrittive
|
||||||
|
continue;
|
||||||
|
if (rin.raggruppabile(rout, campi_riga)) // Se esiste una riga compatibile ...
|
||||||
|
{
|
||||||
|
rout += rin; // ... sommaci la quantita' ecc.
|
||||||
|
elaborata = TRUE; // Ricorda di averla gia' elaborata
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!elaborata) // Se la riga non e' stata gia' sommata ...
|
||||||
|
{
|
||||||
|
TRiga_documento& rout = doc_out.new_row(); // ... crea una riga nuova e ...
|
||||||
|
doc_out.copy_data(rout, rin); // ... copiaci tutti i campi della riga sorgente.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TFatturazione_bolle::elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
||||||
|
const TDate& data_elab)
|
||||||
|
{
|
||||||
|
bool ok = TRUE;
|
||||||
|
|
||||||
|
TToken_string campi_doc(128); // Lista di campi che devono essere uguali
|
||||||
|
campi_doc = "TIPOCF|CODCF|CODVAL|CODLIN"; // Uguali sempre
|
||||||
|
|
||||||
|
// Uguali opzionalmente
|
||||||
|
const char* cond[] = { "CAMBIO", "SCONTO", "TIPODOC", "CODNUM",
|
||||||
|
"CODPAG", "CODABIA|CODCABA", "CODLIST", "CODAG",
|
||||||
|
"CODSPMEZZO", "CODPORTO", "CAUSTRASP", "CODVETT1|CODVETT2|CODVETT3",
|
||||||
|
NULL };
|
||||||
|
for (int u = 0; cond[u]; u++)
|
||||||
|
if (doc_uguale(u)) campi_doc.add(cond[u]);
|
||||||
|
|
||||||
|
for (int id = 0; id < doc_in.items() && ok; id++)
|
||||||
|
{
|
||||||
|
TDocumento& campione = doc_in[id];
|
||||||
|
const int tot = doc_out.items();
|
||||||
|
int od = tot;
|
||||||
|
|
||||||
|
if (campione.raggruppabile()) // Se il documento ha il flag di raggruppabilita' ...
|
||||||
|
{
|
||||||
|
for (od = 0; od < tot; od++) // ... cerca un documento compatibile.
|
||||||
|
{
|
||||||
|
if (campione.raggruppabile(doc_out[od], campi_doc))
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (od >= tot) // Se non ho trovato un documento compatibile ...
|
||||||
|
{ // ... creane uno nuovo (certamente compatibile)
|
||||||
|
const char provv = tipo_numerazione();
|
||||||
|
const int anno = campione.anno();
|
||||||
|
const TString codnum = codice_numerazione_finale();
|
||||||
|
TDocumento* new_doc = new TDocumento(provv, anno, codnum, -1);
|
||||||
|
// Copia i dati della testata
|
||||||
|
TDocumento::copy_data(new_doc->head(), campione.head());
|
||||||
|
|
||||||
|
new_doc->put("DATADOC", data_elab);
|
||||||
|
|
||||||
|
// Aggiungilo alla lista dei documenti in uscita
|
||||||
|
od = doc_out.add(new_doc);
|
||||||
|
}
|
||||||
|
|
||||||
|
ok = raggruppa(campione, doc_out[od]);
|
||||||
|
}
|
||||||
|
return ok;
|
||||||
|
}
|
||||||
|
|
1475
ve/velib04b.cpp
Executable file
1475
ve/velib04b.cpp
Executable file
File diff suppressed because it is too large
Load Diff
561
ve/velib04c.cpp
Executable file
561
ve/velib04c.cpp
Executable file
@ -0,0 +1,561 @@
|
|||||||
|
#include <progind.h>
|
||||||
|
#include <tabutil.h>
|
||||||
|
|
||||||
|
#include <doc.h>
|
||||||
|
#include <rdoc.h>
|
||||||
|
#include <effetti.h>
|
||||||
|
#include <reffetti.h>
|
||||||
|
|
||||||
|
#include "../cg/cgsaldac.h"
|
||||||
|
#include "../ef/ef0101.h"
|
||||||
|
|
||||||
|
#include "velib.h"
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////
|
||||||
|
// TGenerazione_effetti
|
||||||
|
///////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
static TPagamento* _pagamento = NULL;
|
||||||
|
|
||||||
|
TGenerazione_effetti::TGenerazione_effetti(const char* cod)
|
||||||
|
: TElaborazione(cod)
|
||||||
|
{
|
||||||
|
_valid_array.set(2); // tratta
|
||||||
|
_valid_array.set(3); // riba
|
||||||
|
_valid_array.set(5); // paghero'
|
||||||
|
_valid_array.set(7); // tratta accettata
|
||||||
|
_valid_array.set(8); // rapporti interbancari diretti (rid)
|
||||||
|
_valid_array.reset(9); // bonifici
|
||||||
|
|
||||||
|
_docfile = new TLocalisamfile(LF_DOC);
|
||||||
|
_rdocfile = new TLocalisamfile(LF_RIGHEDOC);
|
||||||
|
_cessfile = new TLocalisamfile(LF_CESS);
|
||||||
|
_occas = new TLocalisamfile(LF_OCCAS);
|
||||||
|
_clifo = new TLocalisamfile(LF_CLIFO);
|
||||||
|
_cfven = new TLocalisamfile(LF_CFVEN);
|
||||||
|
_tab = new TLocalisamfile(LF_TAB);
|
||||||
|
_efffile = new TLocalisamfile(LF_EFFETTI);
|
||||||
|
_refffile = new TLocalisamfile(LF_REFFETTI);
|
||||||
|
_cpg = new TTable("%CPG");
|
||||||
|
}
|
||||||
|
|
||||||
|
TGenerazione_effetti::TGenerazione_effetti(const TRectype& rec)
|
||||||
|
: TElaborazione(rec)
|
||||||
|
{
|
||||||
|
_valid_array.set(2); // tratta
|
||||||
|
_valid_array.set(3); // riba
|
||||||
|
_valid_array.set(5); // paghero'
|
||||||
|
_valid_array.set(7); // tratta accettata
|
||||||
|
_valid_array.set(8); // rapporti interbancari diretti (rid)
|
||||||
|
_valid_array.reset(9); // bonifici
|
||||||
|
_docfile = new TLocalisamfile(LF_DOC);
|
||||||
|
_rdocfile = new TLocalisamfile(LF_RIGHEDOC);
|
||||||
|
_cessfile = new TLocalisamfile(LF_CESS);
|
||||||
|
_occas = new TLocalisamfile(LF_OCCAS);
|
||||||
|
_clifo = new TLocalisamfile(LF_CLIFO);
|
||||||
|
_cfven = new TLocalisamfile(LF_CFVEN);
|
||||||
|
_tab = new TLocalisamfile(LF_TAB);
|
||||||
|
_efffile = new TLocalisamfile(LF_EFFETTI);
|
||||||
|
_refffile = new TLocalisamfile(LF_REFFETTI);
|
||||||
|
_cpg = new TTable("%CPG");
|
||||||
|
}
|
||||||
|
|
||||||
|
TGenerazione_effetti::~TGenerazione_effetti()
|
||||||
|
{
|
||||||
|
delete _docfile;
|
||||||
|
delete _rdocfile;
|
||||||
|
delete _cessfile;
|
||||||
|
delete _occas;
|
||||||
|
delete _clifo;
|
||||||
|
delete _cfven;
|
||||||
|
delete _efffile;
|
||||||
|
delete _refffile;
|
||||||
|
delete _tab;
|
||||||
|
delete _cpg;
|
||||||
|
}
|
||||||
|
|
||||||
|
void TGenerazione_effetti::display_error(TDocumento& doc)
|
||||||
|
{
|
||||||
|
TString msg;
|
||||||
|
TString numerazione = doc.numerazione();
|
||||||
|
const long numero = doc.numero();
|
||||||
|
|
||||||
|
switch (_error)
|
||||||
|
{
|
||||||
|
case nr_doc_error:
|
||||||
|
msg.format("Rilevato un numero di documento errato contabilizzando il documento %s/%ld."
|
||||||
|
"Verificare il numero documento e il codice numerazione inseriti in tabella.",(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
case chg_stat_error:
|
||||||
|
msg.format("Rilevato un errore cambiando lo stato al documento %s/%ld."
|
||||||
|
"Verificare l'integrita' del file documenti.",(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
case datadoc_error:
|
||||||
|
msg.format("Rilevato una data documento vuota relativamente al documento %s/%ld."
|
||||||
|
"Verificare l'informazione inserita.",(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
case codpag_error:
|
||||||
|
msg.format("Rilevato un codice pagamento non esistente relativamente al documento %s/%ld."
|
||||||
|
"Verificare l'esistenza del codice pagamento inserito.",(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
case scadenze_error:
|
||||||
|
msg.format("Calcolate 0 scadenze relativamente al documento %s/%ld."
|
||||||
|
"Verificare la correttezza del codice pagamento inserito.",(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
case write_error:
|
||||||
|
if (_efffile->status() != NOERR)
|
||||||
|
msg.format("Si e' verificato l' errore %d in scrittura sul file effetti relativamente al documento %s/%ld"
|
||||||
|
"Verificare la consistenza del file.",_efffile->status(),(const char*)numerazione,numero);
|
||||||
|
else
|
||||||
|
msg.format("Si e' verificato l' errore %d in scrittura sul file righe effetti relativamente al documento %s/%ld"
|
||||||
|
"Verificare la consistenza del file.",_refffile->status(),(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
msg.format("E' stato rilevato un errore generico contabilizzando il documento %s/%ld.",
|
||||||
|
(const char*)numerazione,numero);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
warning_box(msg);
|
||||||
|
_error = no_error; // reset error, as any other one would do, so you can show me the other ones.
|
||||||
|
_can_write = FALSE; // But from now on u cannot write anymore. U must exit this program and repair errors occurred.
|
||||||
|
}
|
||||||
|
|
||||||
|
error_type TGenerazione_effetti::change_doc_status(TDocumento& doc)
|
||||||
|
// Cambia lo stato del documento
|
||||||
|
{
|
||||||
|
doc.stato(get("S4")[0]);
|
||||||
|
if (doc.rewrite() != NOERR)
|
||||||
|
_error = chg_stat_error;
|
||||||
|
return _error;
|
||||||
|
}
|
||||||
|
|
||||||
|
error_type TGenerazione_effetti::change_group_status(TDocumento& doc)
|
||||||
|
// Cambia lo stato dei documenti raggruppati
|
||||||
|
{
|
||||||
|
const int items = _group_array.items();
|
||||||
|
if (items > 0)
|
||||||
|
{
|
||||||
|
_error = no_error;
|
||||||
|
TToken_string * group_element;
|
||||||
|
int i=0;
|
||||||
|
// Ciclo sugli elementi dell'assoc_array
|
||||||
|
for (group_element = (TToken_string *) _group_array.first_item(); group_element != NULL && i < items; i++,group_element = (TToken_string*)_group_array.succ_item())
|
||||||
|
{
|
||||||
|
group_element->restart();
|
||||||
|
const int doc_items = group_element->items();
|
||||||
|
for (int j=0;j<doc_items;j++)
|
||||||
|
{
|
||||||
|
TToken_string t(group_element->get(j),'$');
|
||||||
|
char provv = t.get_char(0);
|
||||||
|
int anno = t.get_int(1);
|
||||||
|
TString codnum(t.get(2));
|
||||||
|
long numdoc = t.get_long(3);
|
||||||
|
if (doc.read(provv,anno,codnum,numdoc) == NOERR) // Legge il documento
|
||||||
|
{
|
||||||
|
doc.put(DOC_STATO,get("S4")[0]);
|
||||||
|
doc.rewrite();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return _error;
|
||||||
|
}
|
||||||
|
|
||||||
|
error_type TGenerazione_effetti::write_groups()
|
||||||
|
{
|
||||||
|
const int items = _effetti_array.items();
|
||||||
|
int err = NOERR;
|
||||||
|
_error = no_error;
|
||||||
|
for (int i = 0; i<items && err == NOERR; i++) // scorre gli effetti generati e li scrive su file
|
||||||
|
{
|
||||||
|
TEffetto& effetto = (TEffetto&)_effetti_array[i];
|
||||||
|
err = effetto.write(*_efffile); // Pensa a tutto lui per rinumerare...
|
||||||
|
}
|
||||||
|
if (err != NOERR)
|
||||||
|
{
|
||||||
|
i--;
|
||||||
|
for (int j = 0; j<i; j++) // rimuove gli effetti raggruppati, per non lasciare documenti raggruppati parzialmente
|
||||||
|
{
|
||||||
|
TEffetto& effetto = (TEffetto&)_effetti_array[j];
|
||||||
|
// posso fare tranquillamente la remove, visto che la numerazione dell'effetto e' gia' stata effettuata
|
||||||
|
effetto.remove(*_efffile);
|
||||||
|
}
|
||||||
|
error_box("Errore %d nella scrittura gruppi di effetti. Nessun raggruppamento effettuato.",err);
|
||||||
|
}
|
||||||
|
return _error;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Criteri di raggruppamento effetti.
|
||||||
|
// Un documento puo' essere raggruppato con i seguenti criteri:
|
||||||
|
// - flag di raggruppamento effetti a TRUE (obbligatorio)
|
||||||
|
// - cliente (obbligatorio)
|
||||||
|
// - valuta (obbligatorio)
|
||||||
|
// - data scadenza (opzionale)
|
||||||
|
// - flag di sosp. d'imposta (opzionale)
|
||||||
|
// - cambio valuta (opzionale)
|
||||||
|
// - cond di pagamento (opzionale)
|
||||||
|
// - banca (opzionale)
|
||||||
|
// - tipo doc. (opzionale)
|
||||||
|
// - cod. numerazione (opzionale)
|
||||||
|
// - agente (opzionale)
|
||||||
|
// I parametri opzionali sono decisi nella tabella elaborazioni
|
||||||
|
// Spiegazione del raggruppamento:
|
||||||
|
// Il raggruppamento di documenti diversi in uno stesso effetto consiste nella creazione
|
||||||
|
// di piu' righe dello stesso effetto.
|
||||||
|
// Ad esempio supponiamo di avere il cliente 10 con 4 fatture ognuna con condizioni di pagamento diverse
|
||||||
|
// la fattura 1 e' suddivisa in 2 rate (10.000 + 30.000)
|
||||||
|
// la fattura 2 e' suddivisa in 4 rate (15.000 + 20.000 + 25.000 + 30.000)
|
||||||
|
// la fattura 3 e' suddivisa in 5 rate (20.000 + 40.000 + 80.000 + 160.000 + 320.000)
|
||||||
|
// la fattura 4 e' suddivisa in 3 rate (50.000 + 100.000 + 150.000)
|
||||||
|
// Il numero di effetti generati equivale al massimo numero di rate (5 in questo caso)
|
||||||
|
// quindi avremo 5 effetti:
|
||||||
|
// il primo avra' 4 righe (prima rata di tutte le fatture)
|
||||||
|
// il secondo avra' 4 righe (seconda rata di tutte le fatture)
|
||||||
|
// il terzo avra' 3 righe (terza rata delle fatture 2,3,4)
|
||||||
|
// il quarto avra' 2 righe (quarta rata delle fatture 2 e 3)
|
||||||
|
// il quinto avra' 1 riga (quinta rata della fattura 3)
|
||||||
|
// La testata di ogni effetto conterra' il totale (somma) dei singoli importi delle righe
|
||||||
|
// ovvero:
|
||||||
|
// tot. primo effetto: 95.000
|
||||||
|
// tot. secondo effetto: 190.000
|
||||||
|
// tot. terzo effetto: 255.000
|
||||||
|
// tot. quarto effetto: 190.000
|
||||||
|
// tot. quinto effetto: 320.000
|
||||||
|
// I dati della testata (soprattutto la data di scadenza) di ogni effetto vengono presi dal
|
||||||
|
// primo documento valido per la generazione dell'effetto corrente:
|
||||||
|
// per i primi due effetti vale la fattura 1
|
||||||
|
// per gli effetti 3 e 4 vale la fattura 2
|
||||||
|
// per l'effetto 5 vale la fattura 3.
|
||||||
|
// Questo e' quanto ho appreso (Hope I'm right...) ;-)
|
||||||
|
|
||||||
|
void TGenerazione_effetti::group_bills(TDocumento& doc)
|
||||||
|
{
|
||||||
|
// Bail out if there aren't items...
|
||||||
|
_error = no_error;
|
||||||
|
const int items = _group_array.items();
|
||||||
|
if (items == 0) return;
|
||||||
|
|
||||||
|
int i=0,j,n,offset=0;
|
||||||
|
TString msg1,msg2;
|
||||||
|
TString16 codpag;
|
||||||
|
real imprata, imprataval, importo, importoval;
|
||||||
|
msg1 = "Raggruppamento effetti";
|
||||||
|
|
||||||
|
#ifdef DBG
|
||||||
|
TProgind p(items,msg1,TRUE,TRUE,1);
|
||||||
|
#else
|
||||||
|
TProgind p(items,msg1,FALSE,TRUE,1);
|
||||||
|
#endif
|
||||||
|
TToken_string * group_element;
|
||||||
|
// Ciclo sugli elementi dell'assoc_array
|
||||||
|
for (group_element = (TToken_string *) _group_array.first_item(); group_element != NULL && i < items; i++,group_element = (TToken_string*)_group_array.succ_item())
|
||||||
|
{
|
||||||
|
#ifdef DBG
|
||||||
|
if (p.iscancelled()) break;
|
||||||
|
#endif
|
||||||
|
p.setstatus(i+1);
|
||||||
|
// Ciclo sui documenti da raggruppare
|
||||||
|
group_element->restart();
|
||||||
|
const int doc_items = group_element->items();
|
||||||
|
for (j=0;j<doc_items;j++)
|
||||||
|
{
|
||||||
|
#ifdef DBG
|
||||||
|
if (p.iscancelled()) break;
|
||||||
|
#endif
|
||||||
|
TToken_string t(group_element->get(j),'$');
|
||||||
|
char provv = t.get_char(0);
|
||||||
|
int anno = t.get_int(1);
|
||||||
|
TString codnum(t.get(2));
|
||||||
|
long numdoc = t.get_long(3);
|
||||||
|
if (doc.read(provv,anno,codnum,numdoc) != NOERR) continue; // Legge il documento (giusto saltare e proseguire se non lo trova?)
|
||||||
|
|
||||||
|
msg2 = "Documento: ";
|
||||||
|
msg2 << codnum << "/" << numdoc;
|
||||||
|
xvt_statbar_set(msg2);
|
||||||
|
do_events();
|
||||||
|
// Ricalcola le scadenze
|
||||||
|
codpag = doc.get(DOC_CODPAG);
|
||||||
|
|
||||||
|
_cpg->put("CODTAB",codpag);
|
||||||
|
if (_cpg->read()!= NOERR)
|
||||||
|
{
|
||||||
|
_error = codpag_error;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
TString16 data(doc.get(DOC_DATAINSC));
|
||||||
|
|
||||||
|
if (data.empty())
|
||||||
|
data = doc.get(DOC_DATADOC);
|
||||||
|
|
||||||
|
const real totale_fatt = doc.totale_doc();
|
||||||
|
const bool valuta = doc.in_valuta();
|
||||||
|
const real change = doc.cambio();
|
||||||
|
const TDate datafatt = doc.get_date(DOC_DATADOC);
|
||||||
|
|
||||||
|
calc_pagamento(doc,codpag,data);
|
||||||
|
CHECK(_pagamento,"Failed to create a TPagamento");
|
||||||
|
const int numrate = _pagamento->n_rate( );
|
||||||
|
if (numrate < 1)
|
||||||
|
{
|
||||||
|
_error = scadenze_error;
|
||||||
|
delete _pagamento;
|
||||||
|
_pagamento = NULL;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Scorre le scadenze
|
||||||
|
for (n = 1; n <= numrate && good(); n++)
|
||||||
|
{
|
||||||
|
// Se non esiste effetto n-esimo (corrisponde al numero di rata corrente+offset)
|
||||||
|
// lo genera con la relativa riga. Se esiste vi somma gli importi ed accoda la riga
|
||||||
|
const bool is_new = n+offset > _effetti_array.items();
|
||||||
|
if (is_new) // Nuovo effetto: crea effetto con i dati di questo documento (e' il primo che incontro nella scansione)
|
||||||
|
{
|
||||||
|
TEffetto effetto;
|
||||||
|
// Setta i dati della testata;
|
||||||
|
effetto.put(EFF_DATASCAD, _pagamento->data_rata(n-1));
|
||||||
|
effetto.put(EFF_TIPOPAG,_pagamento->tipo_rata(n-1));
|
||||||
|
effetto.put(EFF_ULTCLASS,_pagamento->ulc_rata(n-1));
|
||||||
|
effetto.put(EFF_CODCF, doc.get_long(DOC_CODCF));
|
||||||
|
effetto.put(EFF_CODVAL, doc.get(DOC_CODVAL));
|
||||||
|
effetto.put(EFF_CAMBIO, change);
|
||||||
|
effetto.put(EFF_DATACAMBIO,doc.get_date(DOC_DATACAMBIO));
|
||||||
|
effetto.put(EFF_CODABI,doc.get(DOC_CODABIA));
|
||||||
|
effetto.put(EFF_CODCAB,doc.get(DOC_CODCABA));
|
||||||
|
effetto.put(EFF_EFFCOMP,TRUE);
|
||||||
|
_effetti_array.add(effetto);
|
||||||
|
}
|
||||||
|
// aggiorna totale effetto (testata)
|
||||||
|
TEffetto& effetto=(TEffetto&)_effetti_array[n+offset-1];
|
||||||
|
importo = effetto.get_real(EFF_IMPORTO);
|
||||||
|
imprata = _pagamento->importo_rata(n-1,FALSE);
|
||||||
|
importo += imprata;
|
||||||
|
effetto.put(EFF_IMPORTO,importo);
|
||||||
|
if (valuta)
|
||||||
|
{
|
||||||
|
importoval = effetto.get_real(EFF_IMPORTOVAL);
|
||||||
|
imprataval = _pagamento->importo_rata(n-1,TRUE);
|
||||||
|
importoval += imprataval;
|
||||||
|
effetto.put(EFF_IMPORTOVAL,importoval);
|
||||||
|
}
|
||||||
|
// Crea la nuova riga di questo effetto
|
||||||
|
const int rows = effetto.rows_r();
|
||||||
|
TRectype& riga = effetto.row_r(rows+1,TRUE);
|
||||||
|
// reffetto.put(REFF_NPROGTR,nprog);
|
||||||
|
riga.put(REFF_NRIGATR,rows+1);
|
||||||
|
riga.put(REFF_NRATA,n);
|
||||||
|
riga.put(REFF_DATAFATT, datafatt);
|
||||||
|
riga.put(REFF_PROVV,provv);
|
||||||
|
riga.put(REFF_ANNODOC,anno);
|
||||||
|
riga.put(REFF_CODNUM,codnum);
|
||||||
|
riga.put(REFF_NFATT,numdoc);
|
||||||
|
riga.put(REFF_IMPFATT,totale_fatt);
|
||||||
|
riga.put(REFF_IMPORTO,imprata);
|
||||||
|
if (valuta)
|
||||||
|
{
|
||||||
|
riga.put(REFF_IMPFATTVAL,totale_fatt);
|
||||||
|
real totfatlit = totale_fatt*change;
|
||||||
|
riga.put(REFF_IMPFATT,totfatlit);
|
||||||
|
riga.put(REFF_IMPORTOVAL,imprataval);
|
||||||
|
}
|
||||||
|
} // Ciclo sulle scadenze
|
||||||
|
if (_pagamento)
|
||||||
|
{
|
||||||
|
delete _pagamento;
|
||||||
|
_pagamento = NULL;
|
||||||
|
}
|
||||||
|
} // Ciclo sui documenti di questo gruppo
|
||||||
|
offset=_effetti_array.items();
|
||||||
|
} // Ciclo sui gruppi
|
||||||
|
|
||||||
|
// Cambia lo stato a tutti i documenti raggruppati
|
||||||
|
if (good() && _can_write)
|
||||||
|
if (write_groups() == no_error)
|
||||||
|
{
|
||||||
|
_total_bills += _effetti_array.items();
|
||||||
|
change_group_status(doc);
|
||||||
|
}
|
||||||
|
_effetti_array.destroy();
|
||||||
|
_group_array.destroy();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TGenerazione_effetti::valid_type(int pag) const
|
||||||
|
{
|
||||||
|
return _valid_array[pag];
|
||||||
|
}
|
||||||
|
|
||||||
|
void TGenerazione_effetti::calc_pagamento(TDocumento& doc, TString16& codpag, TString16& data)
|
||||||
|
{
|
||||||
|
_pagamento = new TPagamento(codpag, data);
|
||||||
|
const real change = doc.cambio();
|
||||||
|
real totspese = doc.spese();
|
||||||
|
real totimposte = doc.imposta();
|
||||||
|
real totimponibili = doc.totale_doc() - totimposte - totspese;
|
||||||
|
if (doc.in_valuta)
|
||||||
|
{
|
||||||
|
real val1 = totimponibili * change;
|
||||||
|
real val2 = totimposte * change;
|
||||||
|
real val3 = totspese * change;
|
||||||
|
_pagamento->set_total_valuta( totimponibili, totimposte, totspese, change, val1, val2 ,val3);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
_pagamento->set_total( totimponibili, totimposte, totspese );
|
||||||
|
_pagamento->set_rate_auto();
|
||||||
|
}
|
||||||
|
|
||||||
|
void TGenerazione_effetti::generate_bill(TDocumento& doc) // bill in inglese significa anche effetto eheheh ;-)
|
||||||
|
{
|
||||||
|
// That's my JOB!
|
||||||
|
// Ogni rata della fattura (si parla di effetti attivi per ora) genera 1 effetto.
|
||||||
|
// con almeno una riga.
|
||||||
|
// Ad es. Se ho una fattura suddivisa in 3 rate essa generera' 3 effetti con una riga.
|
||||||
|
// Nel caso si decida di raggruppare gli effetti (vedi criteri di raggruppamento)
|
||||||
|
// avro' un effetto con tante righe quante scadenze di fattura sono raggruppabili
|
||||||
|
// Le fatture possono generare effetti solo per i seguenti tipi di pagamento:
|
||||||
|
// 2 - Tratta
|
||||||
|
// 3 - Ri.Ba.
|
||||||
|
// 5 - Paghero'
|
||||||
|
// 7 - Tratta accettata
|
||||||
|
// 8 - Rapporti interbancari diretti
|
||||||
|
// Caso mai tale insieme risultasse incompleto od errato basta solo modificare l'enum posto all'inizio del programma
|
||||||
|
|
||||||
|
TString16 codpag(doc.get(DOC_CODPAG));
|
||||||
|
|
||||||
|
_cpg->put("CODTAB",codpag);
|
||||||
|
if (_cpg->read()!= NOERR)
|
||||||
|
{
|
||||||
|
_error = codpag_error;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
TString16 data(doc.get(DOC_DATAINSC));
|
||||||
|
|
||||||
|
if (data.empty())
|
||||||
|
data = doc.get(DOC_DATADOC);
|
||||||
|
|
||||||
|
const real totale_fatt = doc.totale_doc(); // Importo in valuta
|
||||||
|
if (totale_fatt > ZERO)
|
||||||
|
{
|
||||||
|
const bool valuta = doc.in_valuta();
|
||||||
|
const real change = doc.cambio();
|
||||||
|
|
||||||
|
// calcolo delle scadenze
|
||||||
|
calc_pagamento(doc,codpag,data);
|
||||||
|
|
||||||
|
CHECK(_pagamento,"Failed to create a TPagamento");
|
||||||
|
const int numrate = _pagamento->n_rate( );
|
||||||
|
if (numrate < 1)
|
||||||
|
{
|
||||||
|
_error = scadenze_error;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
_efffile->last();
|
||||||
|
// Variabili per la scrittura dell'effetto
|
||||||
|
long nprog = _efffile->get_long(EFF_NPROGTR)+1;
|
||||||
|
const long codcf = doc.get_long(DOC_CODCF);
|
||||||
|
const TString16 codval(doc.get(DOC_CODVAL));
|
||||||
|
const TDate data_cambio = doc.get_date(DOC_DATACAMBIO);
|
||||||
|
const long codabi = doc.get_long(DOC_CODABIA);
|
||||||
|
const long codcab = doc.get_long(DOC_CODCABA);
|
||||||
|
const TString16 provv(doc.get(DOC_PROVV));
|
||||||
|
const int anno = doc.get_int(DOC_ANNO);
|
||||||
|
const TString16 codnum(doc.get(DOC_CODNUM));
|
||||||
|
const long nfatt = doc.get_long(DOC_NDOC);
|
||||||
|
const TDate datafatt = doc.get_date(DOC_DATADOC);
|
||||||
|
TRectype& effetto = _efffile->curr();
|
||||||
|
TRectype& reffetto = _refffile->curr();
|
||||||
|
real importo;
|
||||||
|
for (int i = 0; i < numrate && good(); i++)
|
||||||
|
{
|
||||||
|
if (valid_type(_pagamento->tipo_rata(i)))
|
||||||
|
{
|
||||||
|
effetto.zero();
|
||||||
|
reffetto.zero();
|
||||||
|
effetto.put(EFF_NPROGTR,nprog);
|
||||||
|
effetto.put(EFF_DATASCAD, _pagamento->data_rata(i));
|
||||||
|
effetto.put(EFF_TIPOPAG,_pagamento->tipo_rata(i));
|
||||||
|
effetto.put(EFF_ULTCLASS,_pagamento->ulc_rata(i));
|
||||||
|
effetto.put(EFF_CODCF, codcf);
|
||||||
|
effetto.put(EFF_CODVAL, codval);
|
||||||
|
if (valuta)
|
||||||
|
{
|
||||||
|
effetto.put(EFF_CAMBIO, change);
|
||||||
|
effetto.put(EFF_DATACAMBIO,data_cambio);
|
||||||
|
}
|
||||||
|
effetto.put(EFF_CODABI,codabi);
|
||||||
|
effetto.put(EFF_CODCAB,codcab);
|
||||||
|
effetto.put(EFF_EFFCOMP,TRUE);
|
||||||
|
if (i == numrate - 1) effetto.put(EFF_ULTRATA,TRUE);
|
||||||
|
// Put sulla riga dell'effetto
|
||||||
|
reffetto.put(REFF_NPROGTR,nprog);
|
||||||
|
reffetto.put(REFF_NRIGATR,1);
|
||||||
|
reffetto.put(REFF_DATAFATT, datafatt);
|
||||||
|
reffetto.put(REFF_NRATA,i+1);
|
||||||
|
reffetto.put(REFF_PROVV,provv);
|
||||||
|
reffetto.put(REFF_ANNODOC,anno);
|
||||||
|
reffetto.put(REFF_CODNUM,codnum);
|
||||||
|
reffetto.put(REFF_NFATT,nfatt);
|
||||||
|
importo = _pagamento->importo_rata(i,FALSE);
|
||||||
|
effetto.put(EFF_IMPORTO,importo);
|
||||||
|
reffetto.put(REFF_IMPFATT,totale_fatt);
|
||||||
|
reffetto.put(REFF_IMPORTO,importo);
|
||||||
|
if (valuta)
|
||||||
|
{
|
||||||
|
importo = _pagamento->importo_rata(i,TRUE); // Importo in valuta
|
||||||
|
real totfatlit = totale_fatt*change; //Not sure about this...
|
||||||
|
effetto.put(EFF_IMPORTOVAL,importo);
|
||||||
|
reffetto.put(REFF_IMPFATTVAL,totale_fatt);
|
||||||
|
reffetto.put(REFF_IMPFATT,totfatlit);
|
||||||
|
reffetto.put(REFF_IMPORTOVAL,importo);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_efffile->write() == NOERR && _refffile->write() == NOERR)
|
||||||
|
{
|
||||||
|
_total_bills++;
|
||||||
|
nprog++;
|
||||||
|
}
|
||||||
|
else _error = write_error;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_pagamento)
|
||||||
|
{
|
||||||
|
delete _pagamento;
|
||||||
|
_pagamento = NULL;
|
||||||
|
}
|
||||||
|
if (good() && _can_write)
|
||||||
|
change_doc_status(doc);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TGenerazione_effetti::elabora(TLista_documenti& doc_in, TLista_documenti& doc_out,
|
||||||
|
const TDate& data_elab)
|
||||||
|
{
|
||||||
|
_pagamento = NULL;
|
||||||
|
_error = no_error;
|
||||||
|
_can_write = TRUE;
|
||||||
|
_total_bills = 0L;
|
||||||
|
|
||||||
|
const int items = doc_in.items(); // Numero dei documenti in questa elaborazione
|
||||||
|
TProgind p(items,"Generazione effetti",FALSE,TRUE,1);
|
||||||
|
for (int i = 0; i < items ; i++) // Scorriamo tutti i documenti nella lista
|
||||||
|
{
|
||||||
|
generate_bill(doc_in[i]); // Genera gli effetti corrispondenti
|
||||||
|
p.setstatus(i+1);
|
||||||
|
if (!good())
|
||||||
|
display_error(doc_in[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Effettua il raggruppamento di eventuali documenti rimasti
|
||||||
|
TDocumento doc;
|
||||||
|
|
||||||
|
if (good())
|
||||||
|
group_bills(doc);
|
||||||
|
|
||||||
|
// Mostra eventuali errori residui
|
||||||
|
if (!good())
|
||||||
|
display_error(doc);
|
||||||
|
|
||||||
|
return _can_write;
|
||||||
|
}
|
||||||
|
|
Loading…
x
Reference in New Issue
Block a user