campo-sirio/ve/velib03.cpp

2435 lines
69 KiB
C++
Raw Normal View History

#include <dongle.h>
#include <modaut.h>
#include <prefix.h>
#include <tabutil.h>
#include <utility.h>
#include "veini.h"
#include "velib.h"
#include "sconti.h"
#include "vepriv.h"
#include "veuml.h"
#include "../cg/cg2103.h"
#include "../cg/cglib01.h"
#include "../mg/mglib.h"
#include "../mg/movmag.h"
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
#include "../pr/prlib.h"
#include "../sv/svlib01.h"
#include "../db/dblib.h"
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
#include <clifo.h>
// calcola il prezzo per le spese
void sppr_calc(const TRectype & rec, const TString & valuta_doc, const real & cambio, real & prezzo, exchange_type controeuro)
{
const TString16 sppr_valuta(rec.get("S4"));
if (sppr_valuta != valuta_doc)
{
const bool prezzo_un = rec.get_char("S6") == 'Q';
if (prezzo_un)
{
TPrice val(prezzo, sppr_valuta);
val.change_value(valuta_doc, cambio, controeuro);
prezzo = val.get_num();
}
else
{
TCurrency val(prezzo, sppr_valuta);
val.change_value(valuta_doc, cambio, controeuro);
prezzo = val.get_num();
}
}
}
///////////////////////////////////////////////////////////
// Movimento di magazzino
///////////////////////////////////////////////////////////
class TMov_mag_doc : public TMov_mag
{
TString_array _codmagc;
protected:
virtual const char * codmag_rauto(int r) const;
public:
void add_magc(const char* magc) { _codmagc.add(magc); }
TMov_mag_doc() { }
virtual ~TMov_mag_doc() {}
};
const char* TMov_mag_doc::codmag_rauto(int r) const
{
TRecord_array & b = body();
if (r > b.rows()) // Can't check non-existent rows
return NULL;
TRectype & row = b[r];
const char tr = row.get_char(RMOVMAG_TIPORIGA);
if (tr != 'D' && tr != 'A') // These are customer's added rows
return NULL;
int j = -1; // Indice per reperire il mag. collegato da _codmagc
for (int i = r; i > 0; i--) // Scorre dalla riga r in su e conta quante righe D
if (b[i].get_char(RMOVMAG_TIPORIGA) == 'D')
j++;
if (j >= 0)
return _codmagc.row(j);
else
return NULL;
}
/////////////////////////////////////////////////////////////
// TRiepilogo IVA
/////////////////////////////////////////////////////////////
TRiepilogo_iva& TRiepilogo_iva::copy(const TRiepilogo_iva& a)
{
(TRectype &) _codiva = (TRectype &) a._codiva;
_imp = a._imp;
_imp_spese = a._imp_spese;
_imp_spese_row = a._imp_spese_row;
_iva = a._iva;
_iva_spese = a._iva_spese;
_sconto_perc = a._sconto_perc;
_sconto_imp = a._sconto_imp;
_iva_sconto = a._iva_sconto;
_tipo = a._tipo;
return *this;
}
TRiepilogo_iva::TRiepilogo_iva(const TCodiceIVA & codiva) : _codiva(codiva)
{
const TString & t =_codiva.tipo();
if (t == "VE")
_tipo = 2;
else
if (t == "ES")
_tipo = 4;
else
if (t == "NI")
_tipo = 8;
else
if (t == "NS")
_tipo = 16;
else
_tipo = 1;
}
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
///////////////////////////////////////////////////////////
// Agenti
///////////////////////////////////////////////////////////
class TAgenti_cache : public TRecord_cache
{
protected:
virtual TObject* rec2obj(const TRectype& rec) const { return new TAgente(rec);}
public:
const TAgente& agente(const char* chiave) { return (const TAgente &) get(chiave);}
TAgenti_cache() : TRecord_cache(LF_AGENTI) {}
virtual ~TAgenti_cache() { }
};
HIDDEN TAgenti_cache * _agenti = NULL;
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
///////////////////////////////////////////////////////////
// Documento per vendite
///////////////////////////////////////////////////////////
long TDocumento::_firm = -1;
TAssoc_array TDocumento::_tipi;
TAssoc_array TDocumento::_numerazioni;
TString16 TDocumento::_codiva_spese;
TString16 TDocumento::_codiva_bolli;
short TDocumento::_has_mag = 3;
short TDocumento::_has_stat_ven = 3;
short TDocumento::_has_provv = 3;
TCodgiac_livelli * TDocumento::_livelli=NULL;
// HIDDEN TStats_agg _st_agg;
HIDDEN TAssoc_array _docs_to_agg;
void TDocumento::init()
{
add_file(LF_RIGHEDOC, "NRIGA");
set_memo_fld("G1");
_tipocf = new TRecfield(*this, "TIPOCF");
_codcf = new TRecfield(*this, "CODCF");
_cod_occas = new TRecfield(*this, "OCFPI");
_provv_agente = new TProvvigioni_agente;
_sconto = _esenzione = NULL;
_stato_originale = ' ';
_dirty_deny = FALSE;
check_modules();
}
TDocumento::TDocumento()
: TMultiple_rectype(LF_DOC)
{
init();
}
TDocumento::TDocumento(const TDocumento & d)
: TMultiple_rectype(LF_DOC)
{
init();
copy(d);
}
TDocumento::TDocumento(char provv, int anno, const char* codnum, long numdoc)
: TMultiple_rectype(LF_DOC)
{
init();
if (numdoc <= 0)
{
numdoc = 0;
set_key(*this, provv, anno, codnum, numdoc);
}
else
read(provv, anno, codnum, numdoc);
}
TDocumento::TDocumento(const TRectype& rec)
: TMultiple_rectype(LF_DOC)
{
init();
read(rec);
}
TDocumento::~TDocumento()
{
delete _tipocf;
delete _codcf;
delete _cod_occas;
if (_provv_agente != NULL) delete _provv_agente;
if (_sconto != NULL) delete _sconto;
if (_esenzione != NULL) delete _esenzione;
}
const TString& TDocumento::codiva_spese() const
{ ((TDocumento *)this)->test_firm(); return _codiva_spese;}
const TString& TDocumento::codiva_bolli() const
{ ((TDocumento *)this)->test_firm(); return _codiva_bolli;}
void TDocumento::check_modules()
{
if (_has_mag == 3)
{
_has_mag = dongle().active(MGAUT);
_has_stat_ven = dongle().active(SVAUT);
_has_provv = dongle().active(PRAUT);
}
}
void TDocumento::set_variables(TExpression * e) const
{
const int items = e->numvar();
for (int i = 0; i < items; i++)
{
const TFieldref field(e->varname(i), LF_DOC);
switch (field.file())
{
case LF_CLIFO :
e->setvar(i, clifor().get(field.name()));
break;
case LF_CFVEN :
e->setvar(i, clifor().vendite().get(field.name()));
break;
default:
e->setvar(i, get(field.name()));
break;
}
}
}
void TDocumento::test_firm()
{
const long new_firm = prefix().get_codditta();
if (_firm != new_firm)
{
TConfig conf(CONFIG_DITTA, "ve");
_codiva_spese = conf.get("SPINCODIVA");
_codiva_bolli = conf.get("SPBOCODIVA");
_firm = new_firm;
}
}
real TDocumento::spese_incasso(int ndec, TTipo_importo t) const
{
real imp_spese;
const real percentuale = get_real("PERCSPINC");
static TArray spese_inc;
if (percentuale > ZERO)
{
if (ndec == AUTO_DECIMALS)
ndec = decimals();
if (spese_inc.objptr(_rim_dir) == NULL)
{
TConfig conf(CONFIG_STUDIO, "ve");
for (TTipo_pag p = _rim_dir; p < _nessun_pag; p = (TTipo_pag) ((int)p + 1))
{
real r(conf.get("IMPSPINC", "ve", p));
spese_inc.add(r, p);
}
}
TPagamento & pag = ((TDocumento *)this)->pagamento();
const int nrate = pag.n_rate();
for (int i = 0; i < nrate; i++)
{
const TTipo_pag p = (TTipo_pag) pag.tipo_rata(i);
imp_spese += (real &) spese_inc[p];
}
imp_spese *= percentuale / 100.0;
if (t == _lordo || t == _imposta)
{
TString16 codiva_es;
iva_esente(codiva_es);
real iva_spese(TRiga_documento::iva(codiva_es.not_empty() ? (const TString &) codiva_es : codiva_spese()).imposta(imp_spese, ndec));
if (t == _lordo)
imp_spese += iva_spese;
else
if (t == _imposta)
imp_spese = iva_spese;
}
const real cambio = get_real("CAMBIO");
if (!cambio.is_zero())
{
const exchange_type ce = get_bool(DOC_CONTROEURO) ? _exchange_contro : _exchange_base;
imp_spese = change_currency(imp_spese, "", ZERO, _exchange_undefined,
get(DOC_CODVAL), cambio, ce, -1);
}
imp_spese.round(ndec);
}
return imp_spese;
}
void TDocumento::iva_esente(TString & codiva_es) const
{
int rows = physical_rows();
codiva_es.cut(0);
for (int r = 1; codiva_es.empty() && r <= rows; r++)
{
const TRiga_documento& riga = ((TDocumento*)this)->row(r);
const TString16 str_codiva(riga.get(RDOC_CODIVA));
if (str_codiva.not_empty())
{
const TCodiceIVA codiva(str_codiva);
const TString & tipoiva = codiva.tipo();
if (tipoiva.empty())
break;
if (tipoiva == "NI")
codiva_es = codiva.codice();
}
}
}
real TDocumento::bolli(real & imp, int ndec, TTipo_importo t) const
{
real tot_bolli;
static TArray sca_bolli;
static TArray imp_bolli;
static real bolli_es;
static real impmin_bolli;
static int nscagl;
if (get_bool("ADDBOLLI"))
{
if (sca_bolli.objptr(0) == NULL)
{
TConfig conf(CONFIG_STUDIO);
bolli_es = (real) conf.get("BOLLIES", "ve");
impmin_bolli = (real) conf.get("IMPMINBOLLI", "ve");
for (nscagl = 0; nscagl < 7; nscagl++)
{
real s(conf.get("SPBOSCA", "ve", nscagl + 1));
real i(conf.get("SPBOIMP", "ve", nscagl + 1));
if (s == ZERO && i == ZERO)
break;
sca_bolli.add(s, nscagl);
imp_bolli.add(i, nscagl);
}
}
if (ndec == AUTO_DECIMALS)
ndec = decimals();
TCurrency_documento imp_val(imp);
imp_val.change_to_firm_val();
real importo = imp_val.get_num();
TPagamento & pag = ((TDocumento*)this)->pagamento();
const int nrate = pag.n_rate();
real old_bolli = -1.00;
real iva_bolli;
TCurrency_documento imp_orig_val(imposta());
imp_orig_val.change_to_firm_val();
const real imp_orig = imp_orig_val.get_num();
TCurrency_documento spese_val(spese());
spese_val.change_to_firm_val();
const real sp_orig = spese_val.get_num();
bool estero = FALSE; // Assumiamo per ora non estero
TString16 codiva_es;
iva_esente(codiva_es);
for (int j = 0; j < 5 && tot_bolli+iva_bolli != old_bolli; j++)
{
old_bolli = tot_bolli + iva_bolli;
const real imposte = imp_orig + iva_bolli;
const real imp_spese = sp_orig + tot_bolli - iva_bolli;
const real imponibile = importo - imposte - imp_spese;
tot_bolli = ZERO;
if (!tipo().nota_credito())
{
real imponibile_esente;
for (int r = physical_rows(); r > 0; r--)
{
const TRiga_documento& riga = ((TDocumento*)this)->row(r);
const TCodiceIVA codiva(riga.get(RDOC_CODIVA));
if (codiva.tipo().not_empty())
imponibile_esente += riga.imponibile();
}
if (imponibile_esente >= impmin_bolli)
tot_bolli = bolli_es;
}
pag.set_total(imponibile, imposte, imp_spese);
pag.set_rate_auto();
for (int i = 0; i < nrate; i++)
{
const TTipo_pag p = (TTipo_pag) pag.tipo_rata(i);
real imp = pag.importo_rata(i);
switch (p)
{
case _ric_ban:
{
int i;
for (i = 0; i < nscagl - 1; i++)
if ((real &) sca_bolli[i] >= imp)
break;
if (imp_bolli.items() > 0)
tot_bolli += (real &) imp_bolli[i];
}
break;
case _tratta:
case _tratta_acc:
{
if (j == 0) // Dobbiamo inizializzare la variabile 'estero'
{
TString16 key;
key.format("%c|%ld", get_char(DOC_TIPOCF), get_long(DOC_CODCF));
const TRectype& clifo = cache().get(LF_CLIFO, key);
const TString& stato_iva = clifo.get(CLI_STATOPAIV);
estero = stato_iva.not_empty() && stato_iva != "IT";
if (!estero)
{
const TString& stato_cf = clifo.get(CLI_STATOCF);
estero = (stato_cf.not_empty() && stato_cf != "IT") || clifo.get_char(CLI_COMCF) == 'Z';
}
}
real r(imp);
const int ndec = decimals();
r.ceil(ndec == 0 ? -3 : 0);
if (estero)
r *= 0.009;
else
r *= 0.012;
r.round(ndec == 0 ? -2 : ndec);
tot_bolli += r;
}
break;
case _cessione:
case _paghero:
case _let_cred:
case _rim_dir:
case _rid:
case _bonfico:
default:
break;
}
}
iva_bolli = TRiga_documento::iva(codiva_es.not_empty() ? (const TString &) codiva_es : codiva_bolli()).imposta(tot_bolli, ndec);
importo += (tot_bolli + iva_bolli - old_bolli);
}
if (t == _lordo)
tot_bolli += iva_bolli;
else
if (t == _imposta)
tot_bolli = iva_bolli;
if (in_valuta())
{
const real cambio = get_real("CAMBIO");
const exchange_type ce = get_bool(DOC_CONTROEURO) ? _exchange_contro : _exchange_base;
tot_bolli = change_currency(tot_bolli, "", ZERO, _exchange_undefined,
get(DOC_CODVAL), cambio, ce, -1);
}
tot_bolli.round(ndec);
}
return tot_bolli;
}
bool TDocumento::modificabile() const
{
const char stato_attuale = stato();
if (stato_attuale <= ' ')
return TRUE;
const TString& stati_modifica = tipo().stati_iniziali_modifica();
return stati_modifica.blank() || stati_modifica.find(stato_attuale) >= 0;
}
bool TDocumento::cancellabile() const
{
const char stato_attuale = stato();
if (stato_attuale <= ' ')
return TRUE;
const TString& stati_cancellazione = tipo().stati_iniziali_cancellazione();
return stati_cancellazione.blank() || stati_cancellazione.find(stato_attuale) >= 0;
}
bool TDocumento::stampabile() const
{
const char stato_attuale = stato();
if (stato_attuale <= ' ')
return TRUE;
if (stato_attuale == tipo().stato_finale_stampa())
return FALSE;
const TString& stati_stampa = tipo().stati_iniziali_stampa();
return stati_stampa.blank() || stati_stampa.find(stato_attuale) >= 0;
}
bool TDocumento::bloccato() const
{
const char stato_attuale = stato();
if (stato_attuale <= ' ')
return FALSE;
char stato_bloccato = tipo().stato_bloccato();
if (stato_bloccato <= ' ')
return FALSE;
return stato_attuale >= stato_bloccato;
}
// Funzione statica utile a tutti gli utenti di LF_DOC e LF_RIGHEDOC
void TDocumento::set_key(TRectype& rec, char provv, int anno, const char* codnum, long numdoc)
{
CHECK(provv == 'D' || provv == 'P', "Provvisorio o Definitivo?");
CHECKD(anno > 1900, "Anno non valido: ", anno);
CHECK(codnum && *codnum, "Codice numerazione nullo");
CHECKD(numdoc >= 0, "Numero documento non valido ", numdoc);
rec.put("PROVV", provv);
rec.put("ANNO", anno);
rec.put("CODNUM", codnum);
rec.put("NDOC", numdoc);
}
// Funzione statica utile a tutti gli utenti di LF_DOC e LF_RIGHEDOC
void TDocumento::copy_data(TRectype& dst, const TRectype& src)
{
// Memorizza tutti i campi chiave
const char provv = dst.get_char(RDOC_PROVV);
const int anno = dst.get_int(RDOC_ANNO);
const TString4 codnum = dst.get(RDOC_CODNUM);
const long numdoc = dst.get_long(RDOC_NDOC);
const int nriga = dst.num() == LF_RIGHEDOC ? dst.get_int(RDOC_NRIGA) : 0;
const long idriga = dst.num() == LF_RIGHEDOC ? dst.get_long(RDOC_IDRIGA) : 0;
// Copia tutto il record
dst = src;
// Ripristina tutti i campi chiave
set_key(dst, provv, anno, codnum, numdoc);
if (nriga > 0)
{
dst.put(RDOC_NRIGA, nriga);
dst.put(RDOC_IDRIGA, idriga);
dst.zero(RDOC_MOVMAG);
const TString memo = src.get(RDOC_DESCEST);
dst.put(RDOC_DESCEST, memo);
}
else
dst.zero(DOC_MOVMAG);
}
// Funzione statica utile a tutti gli utenti di LF_RIGHEDOC
void TDocumento::copy_data(TRiga_documento& dst, const TRiga_documento& src)
{
copy_data((TRectype&)dst, (const TRectype&)src);
dst.put(RDOC_CODCMS, src.codice_commessa());
dst.put(RDOC_FASCMS, src.fase_commessa());
}
void TDocumento::copy_contents(const TDocumento& src)
{
copy_data(head(), src.head());
destroy_rows();
const int rows = src.physical_rows();
for (int i = 1; i <= rows ; i++)
{
const TRiga_documento& s = src[i];
TRiga_documento & r = new_row(s.tipo().codice());
copy_data(r, s);
r.set_original_rdoc_key(s);
}
}
TRiga_documento& TDocumento::insert_row(int row, const char *tipo)
{
TRiga_documento & r = (TRiga_documento &) TMultiple_rectype::insert_row(row); // ok
if (tipo)
r.set_tipo(tipo);
return r;
}
TRiga_documento& TDocumento::new_row(const char *tipo)
{
TRiga_documento & r = (TRiga_documento&)TMultiple_rectype::new_row(); // ok
if (tipo)
r.set_tipo(tipo);
return r;
}
int TDocumento::read(TBaseisamfile& f, word op, word lockop)
{
int err = TMultiple_rectype::read(f, op ,lockop);
_cli_for.zero();
_occas.zero();
set_riga_sconto();
if (is_fattura())
set_riga_esenzione();
_stato_originale = stato();
if (err == NOERR && tipo_valido() && tipo().statistiche() && _has_stat_ven)
{
TString80 key(get(DOC_PROVV)); key << get(DOC_ANNO); key << get(DOC_CODNUM); key << get(DOC_NDOC);
TObject * o = _docs_to_agg.objptr(key);
const bool is_nota_credito = tipo().nota_credito();
if ( lockop >= _lock && o == NULL)
{
TStats_agg * st_agg = new TStats_agg;
for (int i = physical_rows(); i > 0; i--)
if (is_nota_credito)
st_agg->add(row(i));
else
st_agg->sub(row(i));
_docs_to_agg.add(key, st_agg, TRUE);
}
else
if (lockop == _unlock && o != NULL)
_docs_to_agg.remove(key);
}
if (err == NOERR && _has_provv)
_old_agente = get(DOC_CODAG);
else
_old_agente.cut(0);
return err;
}
int TDocumento::read(char provv, int anno, const char* codnum, long numdoc, word op, word lockop)
{
CHECK(numdoc > 0, "Numero documento nullo.");
zero();
set_key(*this, provv, anno, codnum, numdoc);
return read(op, lockop);
}
long TDocumento::renum_ndoc(long numdoc)
{
if (numdoc <= 0)
{
const char tn = tipo_numerazione();
const int an = anno();
const TString4 nu = numerazione();
numdoc = get_next_key(tn, an, nu);
}
put(DOC_NDOC, numdoc); // Aggiorna testata
TMultiple_rectype::renum_key(); // Aggiorna righe ok
return numdoc;
}
void TDocumento::set_riga_sconto()
{
const TString80 sconto(get("SCONTOPERC"));
if (sconto.empty())
{
if(_sconto != NULL)
delete _sconto;
_sconto = NULL;
}
else
{
if (_sconto == NULL)
{
static TString16 _tipo_riga_sc;
if (_tipo_riga_sc.empty())
{
TConfig conf(CONFIG_STUDIO, "ve");
_tipo_riga_sc = conf.get("TRSCONTI", "ve");
// Se non esiste il tipo riga lo cerca, lo setta di default ed avvisa
if (_tipo_riga_sc.empty())
{
_tipo_riga_sc = "08";
conf.set("TRSCONTI", _tipo_riga_sc);
warning_box("Il tipo riga sconti di testa non risultava impostato.\n L'applicazione usera' automaticamente il tipo %s", (const char*) _tipo_riga_sc);
}
}
_sconto = new TRiga_documento(this, _tipo_riga_sc);
_sconto->put("DESCR","Sconto");
}
_sconto->put("SCONTO", sconto);
}
}
void TDocumento::set_riga_esenzione()
{
TCli_for & c = clifor();
const TCodiceIVA codes(c.vendite().get(CFV_ASSFIS));
const TString16 v_esenzione(c.vendite().get(CFV_VSPROT));
const TString16 v_data_esenzione(c.vendite().get(CFV_VSDATAREG));
const TString16 n_registrazione(c.vendite().get(CFV_NSPROT));
const TString16 n_data_registrazione(c.vendite().get(CFV_NSDATAREG));
bool esente = codes.tipo().not_empty() && v_esenzione.not_empty() &&
v_data_esenzione.not_empty() && n_registrazione.not_empty() &&
n_data_registrazione.not_empty();
if (esente)
{
esente = false;
const TString8 codiva = codes.codice();
for (int i = physical_rows(); !esente && i > 0; i--)
esente = row(i).get(RDOC_CODIVA) == codiva;
}
if (!esente)
{
if(_esenzione != NULL)
delete _esenzione;
_esenzione = NULL;
}
else
{
static TString4 _tipo_riga_es;
static TString80 _des_esenz;
static real _bollo_es;
if (_tipo_riga_es.empty())
{
TConfig conf(CONFIG_STUDIO, "ve");
_tipo_riga_es = conf.get("TRESENZ", "ve");
_bollo_es = (real)conf.get("BOLLIES", "ve");
if (_tipo_riga_es.empty())
{
_tipo_riga_es = "05";
conf.set("TRESENZ", _tipo_riga_es);
warning_box("Il tipo riga esenzione non risultava impostato.\n L'applicazione usera' automaticamente il tipo %s", (const char*) _tipo_riga_es);
}
_des_esenz = conf.get("DESESENZ", "ve");
if (_des_esenz.not_empty())
_des_esenz.insert(" ");
_des_esenz.insert("Fattura non imponibile");
}
if (_esenzione == NULL)
_esenzione = new TRiga_documento(this, _tipo_riga_es);
TString d(256); d = _des_esenz;
d << format(" come da vostra dichiarazione n. %s del %s da noi annotata al n. %s il %s.",
(const char *) v_esenzione, (const char *) v_data_esenzione,
(const char *) n_registrazione, (const char *) n_data_registrazione);
_esenzione->put(RDOC_DESCR, d.left(50));
_esenzione->put(RDOC_DESCLUNGA, "X");
_esenzione->put(RDOC_DESCEST, d.mid(50));
}
}
void TDocumento::dirty_fields()
{
if (!_dirty_deny)
{
for (TDocumento_variable_field * f = (TDocumento_variable_field *) first_variable_field();
f != NULL; f = (TDocumento_variable_field *) succ_variable_field())
f->set_dirty();
dirty_tabella_iva();
for (int i = loaded_rows(); i > 0; i--)
{
TRiga_documento & r = (TRiga_documento &) row(i);
r.dirty_fields(FALSE);
}
_dirty_deny = TRUE;
}
}
int TDocumento::write_rewrite(TBaseisamfile & f, bool re) const
{
TDocumento & myself = *((TDocumento *)this);
const bool new_doc = nuovo() || numero() <= 0; // E' nuovo di zecca!
if (new_doc)
{
char stato_finale = tipo().stato_finale_inserimento();
if (stato() == '\0' && stato_finale > ' ')
myself.stato(stato_finale);
}
else
myself._stato_originale = stato();
const bool doc_bloccato = bloccato();
const char stato_doc(stato());
const int rows = physical_rows();
int err = NOERR;
if (!doc_bloccato)
{
if(tipo().spese_aut() && !get_bool("SPESEUPD"))
{
TString16 name("CODSP0");
TString_array spese;
TRectype & ven_rec = clifor().vendite();
for (int i = 1; i <= 4; i++)
{
name.rtrim(1); name << i;
const TString16 s(ven_rec.get(name));
if (s.not_empty())
spese.add(s);
}
myself.update_spese_aut(spese);
}
myself.update_conai();
myself.set_row_ids();
long num = get_long("MOVMAG");
const bool check_movmag = dongle().active(MGAUT) && tipo().mov_mag();
if (check_movmag)
{
const bool do_movmag = tipo().stato_with_mov_mag(stato_doc) && get(DOC_CAUSMAG).not_empty();
TMov_mag_doc mov;
TLocalisamfile m(LF_MOVMAG);
mov.zero();
if (num == 0 && do_movmag)
{
err = mov.write(m);
if (err != NOERR)
return err;
num = mov.get_long(MOVMAG_NUMREG);
myself.put("MOVMAG", num);
}
if (num > 0)
{
const bool scarica_residuo = tipo().scarica_residuo();
mov.put(MOVMAG_NUMREG, num);
while (mov.read(m, _isequal, _testandlock) == _islocked)
message_box("Movimento di magazzino n. %ld in uso da parte di un'altro utente", num);
if (do_movmag)
{
TRecord_array & b = mov.body();
const int mag_rows = mov.rows();
int i;
for (i = mag_rows; i > 0; i--)
{
TRectype & r = b[i];
if (r.get_char(RMOVMAG_TIPORIGA) == riga_dadocumento)
{
b.destroy_row(i);
if (b.exist(i + 1) &&
b[i + 1].get_char(RMOVMAG_TIPORIGA) == riga_automatica)
b.destroy_row(i + 1);
}
else
if (r.get_bool(RMOVMAG_ESPLOSA))
b.destroy_row(i);
}
b.pack();
const TDate d(get("DATADOC"));
TString8 codes; codes.format("%04d", mov.codice_esercizio(d));
mov.put(MOVMAG_ANNOES, codes);
mov.put(MOVMAG_DATAREG, d);
mov.put(MOVMAG_DATACOMP, d);
mov.put(MOVMAG_DOCPROVV, get("PROVV"));
mov.put(MOVMAG_ANNODOC, get("ANNO"));;
mov.put(MOVMAG_CODNUM, get("CODNUM"));
long numdoc = get_long("NDOC");
if (numdoc <= 0L)
numdoc = myself.renum_ndoc(numdoc);
mov.put(MOVMAG_NUMDOC, numdoc);
const long ex_numdoc = get_long("NUMDOCRIF");
if (ex_numdoc == 0)
{
mov.put(MOVMAG_EXNUMDOC, numdoc);
mov.put(MOVMAG_EXDATADOC, d);
}
else
{
mov.put(MOVMAG_EXNUMDOC, ex_numdoc);
const TDate ex_d(get("DATADOCRIF"));
mov.put(MOVMAG_EXDATADOC, ex_d);
}
mov.put(MOVMAG_CATVEN, get("CATVEN"));
mov.put(MOVMAG_CODLIST, get("CODLIST"));
mov.put(MOVMAG_CODCONT, get("CODCONT"));
mov.put(MOVMAG_CODCAMP, get("CODCAMP"));
mov.put(MOVMAG_CODCAUS, get("CAUSMAG"));
TString8 codnum(numerazione());
mov.put(MOVMAG_DESCR, format("%s %s n. %ld del %s", (const char *) tipo().get("S1"),(const char *)codnum, numdoc, (const char *) d.string()));
mov.put(MOVMAG_TIPOCF, get("TIPOCF"));
mov.put(MOVMAG_CODCF, get("CODCF"));
int j = 1;
real cambio = ZERO;
if (get(DOC_CODVAL).not_empty())
cambio = get_real(DOC_CAMBIO);
if (cambio == ZERO)
cambio = 1.0;
const bool esplodente = TCausale_magazzino(mov.get(DOC_CAUSMAG)).esplodente();
TString80 codice_riga;
TString16 caus_riga;
TDistinta_tree dist;
TString80 codart;
for (i = 1; i <= rows; i++)
{
TRiga_documento & r = myself.row(i);
const bool articolo = r.is_articolo();
codart = r.get("CODARTMAG");
codice_riga = r.get("CODART");
if (codart.empty())
codart = codice_riga;
caus_riga = r.get("CAUSMAG");
bool distinta_da_esplodere = FALSE;
if (!articolo &&
(codice_riga.not_empty() &&
(caus_riga.not_empty() ? TCausale_magazzino(caus_riga).esplodente() : esplodente)))
distinta_da_esplodere = dist.set_root(TCodice_articolo(codice_riga));
if (articolo || distinta_da_esplodere)
{
long r_num = r.get_long("MOVMAG");
if (r_num == 0)
{
r_num = num;
r.put("MOVMAG", r_num);
}
const real qta = scarica_residuo ? r.qtaresidua(): r.quantita();
if (r_num == num && qta != ZERO)
{
TRectype & rm = mov.insert_row(j++);
mov.add_magc(r.get("CODMAGC"));
rm.put(RMOVMAG_IMPIANTO, r.get("IMPIANTO"));;
rm.put(RMOVMAG_LINEA, r.get("LINEA"));
rm.put(RMOVMAG_CODMAG, r.get("CODMAG"));
rm.put(RMOVMAG_CODART, codart);
rm.put(RMOVMAG_LIVGIAC, r.get("LIVELLO"));
rm.put(RMOVMAG_UM, r.get("UMQTA"));
rm.put(RMOVMAG_QUANT, qta);
TCurrency_documento prezzo(r.prezzo(TRUE, FALSE), *this, TRUE);
prezzo.change_to_firm_val();
rm.put(RMOVMAG_PREZZO, prezzo.get_num());
rm.put(RMOVMAG_CODCAUS, caus_riga);
rm.put(RMOVMAG_TIPORIGA, (char) riga_dadocumento);
}
}
}
mov.rewrite(m);
}
else
{
mov.remove(m);
for (int i = rows; i > 0; i--)
{
TRiga_documento & r = myself.row(i);
r.zero("MOVMAG");
}
myself.zero("MOVMAG");
}
}
}
}
{
TLocalisamfile anamag(LF_ANAMAG);
TLocalisamfile codalt(LF_CODCORR);
codalt.setkey(2);
bool docevaso = TRUE;
const TDate datacons(get_date(DOC_DATACONS));
const TString80 codcms(get(DOC_CODCMS));
const TString80 fascms(get(DOC_FASCMS));
const TString80 codcos(get(DOC_CODCOSTO));
for (int i = rows; i > 0; i--)
{
TRiga_documento& r = myself.row(i);
if ((r.is_merce() || r.is_omaggio()) && !r.is_checked())
{
if (r.get(RDOC_CODARTMAG) == NULL_CODART)
r.put(RDOC_CODARTMAG, "");
else
{
const TString & codart = r.get("CODART");
anamag.put("CODART", codart);
if (anamag.read() == NOERR)
r.put("CODARTMAG", codart);
else
{
codalt.put("CODARTALT", codart);
if (codalt.read() == NOERR)
r.put("CODARTMAG", codalt.get("CODART"));
}
r.checked();
}
}
if (r.is_evadibile() && is_ordine())
{
docevaso &= r.is_evasa();
const TDate dcons = r.get_date(RDOC_DATACONS);
if (!dcons.ok())
r.put(RDOC_DATACONS, datacons);
}
if (r.get(RDOC_CODCMS).blank() && r.get(RDOC_FASCMS).blank() && r.get(RDOC_CODCOSTO).blank())
{
r.put(RDOC_CODCMS, codcms);
r.put(RDOC_FASCMS, fascms);
r.put(RDOC_CODCOSTO, codcos);
}
}
if (is_ordine())
((TDocumento *)this)->put(DOC_DOCEVASO, docevaso); // Tutte le righe evase -> doc evaso
} // Almeno una riga aperta -> doc aperto
err = TMultiple_rectype::write_rewrite(f, re);
if (!doc_bloccato && err == NOERR)
{
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
if (clifor().occasionale())
{
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
if (get("OCFPI").not_empty())
{
TLocalisamfile o(LF_OCCAS);
TOccasionale & occ = occas();
err = occ.write(o);
if (err == _isreinsert)
err = occ.rewrite(o);
}
}
if (_has_provv && tipo().provvigioni() && tipo().stato_provvigioni() <= stato())
{
const TString16 agente = get(DOC_CODAG);
if (agente != _old_agente)
{
if (_old_agente.not_empty())
{
const int anno = get_int(DOC_ANNO);
const TString16 codnum = get(DOC_CODNUM);
const long numdoc = get_long(DOC_NDOC);
TProvvigioni_agente provv;
if (provv.read(_old_agente, anno, codnum, numdoc) == NOERR)
provv.remove();
}
myself._old_agente = agente;
}
if (agente.not_empty())
myself.write_provvigioni();
}
if (tipo().statistiche() && _has_stat_ven)
{
TString80 key(get(DOC_PROVV)); key << get(DOC_ANNO); key << get(DOC_CODNUM); key << get(DOC_NDOC);
TStats_agg * st_agg = (TStats_agg *) _docs_to_agg.objptr(key);
const bool is_nota_credito = tipo().nota_credito();
if (st_agg == NULL)
{
st_agg = new TStats_agg;
_docs_to_agg.add(key, st_agg, TRUE);
}
int i;
for (i = physical_rows(); i > 0; i--)
if (is_nota_credito)
st_agg->sub(myself.row(i));
else
st_agg->add(myself.row(i));
st_agg->update();
for (i = physical_rows(); i > 0; i--)
if (is_nota_credito)
st_agg->add(myself.row(i));
else
st_agg->sub(myself.row(i));
}
}
return err;
}
// eliminare anche il mov di mag. ??????
int TDocumento::remove(TBaseisamfile& f) const
{
if (!cancellabile() && !yesno_box("Documento non cancellabile,\nContinuare ugualmente"))
return NOERR;
const bool check_movmag = dongle().active(MGAUT) && tipo().mov_mag();
if (check_movmag)
{
const long num = get_long("MOVMAG");
if (num > 0)
{
TMov_mag_doc mov;
TLocalisamfile m(LF_MOVMAG);
mov.put(MOVMAG_NUMREG, num);
while (mov.read(m, _isequal, _testandlock) == _islocked)
message_box("Movimento di magazzino in uso da parte di un'altro utente");
mov.remove(m);
}
}
if (tipo().statistiche() && _has_stat_ven)
{
TString80 key(get(DOC_PROVV)); key << get(DOC_ANNO); key << get(DOC_CODNUM); key << get(DOC_NDOC);
TStats_agg * st_agg = (TStats_agg *) _docs_to_agg.objptr(key);
if (st_agg != NULL)
{
st_agg->update();
_docs_to_agg.remove(key);
}
}
if (_has_provv && tipo().provvigioni())
{
const TString8 agente(get(DOC_CODAG));
const int anno = TDocumento::anno();
const TString4 codnum(numerazione());
const long ndoc = numero();
// Legge le provvigioni per questo documento
_provv_agente->read(agente, anno,codnum,ndoc);
// Le rimuove
_provv_agente->remove();
}
return TMultiple_rectype::remove(f);
}
int TDocumento::decimals(bool price) const
{
const TString4 codval(get(DOC_CODVAL));
const TExchange exc(codval);
const int ndec = exc.decimals(price);
return ndec;
}
void TDocumento::flush_rows()
{
remove_body(LF_RIGHEDOC);
}
TProvvigioni_agente& TDocumento::calc_provvigioni(const bool generata)
{
CHECK (_provv_agente, "Bad TProvvigione_agente object");
TString16 agente(get(DOC_CODAG));
const int anno = TDocumento::anno();
TString16 codnum(numerazione());
const long ndoc = numero();
TDate datadoc(data());
while (_provv_agente->read(agente, anno,codnum,ndoc) == _islocked) // Legge le provvigioni per questo documento
if (!yesno_box("Dati agente %s in uso da un altro utente. Riprovare?", (const char*) agente))
return *_provv_agente;
const TString16 codval(TDocumento::valuta());
const real change(cambio());
const real perc = _provv_agente->perc_fatt();
TCurrency_documento tot_doc(totale_doc(), *this);
TCurrency_documento tot_netto(totale_netto(), *this);
TCurrency_documento tot_provv(provvigione(), *this);
TCurrency_documento provv_fat((tot_provv.get_num() / 100.0) * perc, *this); // Provvigione sul fatturato (rata 0)
// const int ndec = decimals();
// provv_fat.round(ndec);
TCurrency_documento provv_pag = tot_provv - provv_fat; // Provvigione sul pagato (da suddivere secondo il pagamento)
const bool valuta = in_valuta();
// Calcolo rate per provvigioni e documento
TPagamento& pag1 = pagamento(); // Per rate documento
TPagamento* pag2 = new TPagamento(pag1.code(), datadoc.string()); // Per rate documento
// Rilegge il pagamento, nel caso in cui venga chiamata la scrittura del documento
// corrente dopo che <20> stata effettuata una contabilizzazione; la contabilizzazione
// nel caso di anticipo aggiunge una rata in pi<70>
if (pag1.n_rate() > pag2->n_rate())
pag1.read();
TCurrency_documento totspese(spese(), *this);
TCurrency_documento totimposte(imposta(), *this);
TCurrency_documento totimponibili(tot_doc - totimposte - totspese);
TCurrency_documento anticipo(get_real(DOC_IMPPAGATO), *this);
if (is_nota_credito()) // Se il documento e' una nota di credito, cambia segno
{
tot_doc = -tot_doc;
tot_netto = -tot_netto;
tot_provv = -tot_provv;
provv_fat = -provv_fat;
provv_pag = -provv_pag;
totspese = -totspese;
totimposte = -totimposte;
totimponibili = -totimponibili;
}
// Considera l'anticipo, come in contabilizzazione ed in generazione effetti
//
// Un anticipo su di una nota di credito non dovrebbe comunque mai esistere, non ha senso.
// Se esiste <20> un errore in inserimento da parte del cliente.
if (anticipo.get_num() < abs(tot_doc.get_num()))
{
TGeneric_distrib d(anticipo.get_num(), decimals());
d.add(totimponibili.get_num());
d.add(totimposte.get_num());
d.add(totspese.get_num());
const TCurrency_documento pagtotimponibili(totimponibili.get_num() - d.get(), *this);
const TCurrency_documento pagtotimposte(totimposte.get_num() - d.get(), *this);
const TCurrency_documento pagtotspese(totspese.get_num() - d.get(), *this);
TCurrency zero(ZERO);
if (valuta)
{
//real val1 = totimponibili * change;
TCurrency_documento val2(pagtotimposte); val2.change_to_firm_val();
TCurrency_documento val3(pagtotspese); val3.change_to_firm_val();
TCurrency_documento val1(tot_doc); val1.change_to_firm_val(); val1 -= val2 - val3;
pag1.set_total_valuta(pagtotimponibili, pagtotimposte, pagtotspese, val1, val2, val3);
TCurrency_documento provv_pag_base(provv_pag) ; provv_pag_base.change_to_firm_val();
pag2->set_total_valuta(provv_pag, zero, zero, provv_pag_base, zero, zero);
}
else
{
pag1.set_total(pagtotimponibili, pagtotimposte, pagtotspese);
pag2->set_total(provv_pag, zero, zero);
}
pag1.set_rate_auto();
pag2->set_rate_auto();
}
else
{
pag1.zap_rate();
pag2->zap_rate();
}
const bool is_anticipo = anticipo.get_num() > ZERO;
if (is_anticipo)
{
pag1.add_rata();
TDate first_scad(pag1.data_rata(0));
if (datadoc == first_scad)
pag1.set_datarata(0, ++first_scad);
for (int k=pag1.n_rate()-1; k>0; k--)
pag1.rata(k) = pag1.rata(k-1);
if (anticipo >= tot_doc)
anticipo = tot_doc;
TCurrency_documento anticipo_base(anticipo); anticipo_base.change_to_firm_val();
pag1.set_rata(0, valuta ? anticipo.get_num() : ZERO, anticipo_base.get_num(), datadoc, 1, "", FALSE);
}
// Crea le nuove rate provvigionali
const bool isnew = _provv_agente->items() == 0; // Il documento non ha righe provvigionali
TRate_doc& rd = _provv_agente->rate(anno, codnum, ndoc, isnew ? TRUE : FALSE);
// A questo punto rd e' vuoto: settiamo i dati del documento:
TToken_string t;
t.add(anno); t.add(codnum);t.add(ndoc);
t.add(datadoc.string()); t.add(tot_doc.string());
t.add(tot_provv.string());t.add(tot_netto.string());
t.add(codcf());
t.add(TDocumento::valuta());t.add(change.string());
t.add(get(DOC_DATACAMBIO));
rd.set(t);
// Adesso si possono aggiungere le rate (per quelle gia' esistenti sostituisce solo alcuni valori)
// - Rata 0 : importo rata = 0; importo provvigione = provvigione all'atto della fattura (percentuale sugli agenti)
// data scadenza viene settata uguale alla data documento
// la provvigione rimanente va suddivisa in rate a seconda del codice pagamento
// Nel caso si ha un anticipo documento, l'importo della rata non sar<61> 0 ma eguale all'anticipo stesso
// Se poi abbiamo il caso in cui l'anticipo paga completamente il documento
// non avremo alcuna rata e tutto l'importo della provvigione del doc. andr<64> comunque
// sulla rata 0, anche se la provvigione sul fatturato <20> 0 (% a 0)
const int nrate = pag1.n_rate();
if (nrate == 1 && is_anticipo) // significa che l'anticipo paga tutto ora, quindi provv_fat vale tutta la provvigione del documento
provv_fat = tot_provv;
const bool first_rata_ok = provv_fat.get_num() != ZERO;
// Impostazione prima rata solo se la provvigione sul fatturato <20> diversa da 0
if (first_rata_ok)
{
TRata& rt = rd.row(0,TRUE);
rt.set_rata(0); rt.set_datascad(datadoc); rt.set_tipopag(1);
rt.set_imprata(anticipo.get_num()); rt.set_impprovv(provv_fat.get_num());
if (generata)
rt.set_generata();
}
// Setta le rate rimanenti
int i;
for (i = 1; i <= nrate; i++)
{
if (i == nrate && is_anticipo)
break;
const int index = is_anticipo ? i : i - 1;
TRata& rt = rd.row(first_rata_ok ? i : i - 1, TRUE);
rt.set_rata(i);
rt.set_datascad(pag1.data_rata(index));
rt.set_tipopag(pag1.tipo_rata(index));
rt.set_imprata(pag1.importo_rata(index,valuta ? TRUE : FALSE));
rt.set_impprovv(pag2->importo_rata(i-1,valuta ? TRUE : FALSE));
if (generata)
rt.set_generata();
}
// Rimuove eventuali righe in eccesso
const int rd_items = rd.items(); // Rate precedenti
for (i = first_rata_ok ? nrate+1 : nrate; i < rd_items; i++)
rd.remove_rata(i);
delete pag2;
return *_provv_agente;
}
bool TDocumento::in_valuta() const
{
const TString& val = valuta();
return is_true_value(val);
}
TCodgiac_livelli & TDocumento::livelli() const
{
if (_livelli == NULL)
_livelli = new TCodgiac_livelli();
return *_livelli;
}
TRiga_documento & TDocumento::row(int index)
{
TRecord_array & b = body();
const int nrows = b.rows();
TRiga_documento * r = NULL;
if (index <= nrows)
{
r = &((TRiga_documento &) b.row(index, FALSE));
CHECKD(r, "Riga documento non esistente ", index);
}
else
{
CHECKD((index == nrows + 1 && (_sconto != NULL || _esenzione != NULL)) || (index == nrows + 2 && _sconto != NULL && _esenzione != NULL),
"Riga documento non esistente ", index);
if (index == nrows + 1)
{
r = _sconto != NULL ? _sconto : _esenzione;
}
if (index == nrows + 2)
r = _esenzione;
}
return *r;
}
const TRiga_documento& TDocumento::physical_row(int index) const
{
TRecord_array & b = body();
return (TRiga_documento&)b.row(index, FALSE);
}
long TDocumento::get_next_key(char provv, int anno, const char* codnum) const
{
long n = 0;
TLocalisamfile doc(LF_DOC);
TRectype& curr = doc.curr();
set_key(curr, provv, anno, codnum, 9999999L);
const int err = doc.read(_isgreat);
if (err != _isemptyfile)
{
if (err == NOERR)
doc.prev();
if (curr.get_char("PROVV") == provv &&
curr.get_int("ANNO") == anno &&
curr.get("CODNUM") == codnum)
n = curr.get_long("NDOC");
}
n++;
return n;
}
const TTipo_documento& TDocumento::tipo(const char * tipodoc)
{
CHECK(tipodoc && *tipodoc, "Tipo documento nullo");
TTipo_documento * o = (TTipo_documento*)_tipi.objptr(tipodoc);
if (o == NULL)
{
o = new TTipo_documento(tipodoc);
_tipi.add(tipodoc, o);
}
return *o;
}
const TTipo_documento& TDocumento::tipo() const
{
const TString16 tipodoc(get("TIPODOC"));
return tipo(tipodoc);
}
const TCodice_numerazione& TDocumento::codice_numerazione(const char * numerazione)
{
TCodice_numerazione* o = (TCodice_numerazione*)_numerazioni.objptr(numerazione);
if (o == NULL)
{
o = new TCodice_numerazione(numerazione);
_numerazioni.add(numerazione, o);
}
return *o;
}
const TCodice_numerazione& TDocumento::codice_numerazione() const
{
return codice_numerazione(numerazione());
}
bool TDocumento::raggruppabile(const TDocumento& doc, TToken_string& campi) const
{
bool ok = raggruppabile() && doc.raggruppabile();
if (ok)
{
TString campo;
for (const char* c = campi.get(0); c && ok; c = campi.get())
{
if (strncmp(c, "CODABI", 6) == 0 || strncmp(c, "CODCAB", 6) == 0)
{
long cod = get_long(c);
ok &= (cod == doc.get_long(c));
}
else
{
campo = get(c);
ok &= campo == doc.get(c);
}
}
}
return ok;
}
void TDocumento::set_fields(TAuto_variable_rectype & rec)
{
if (tipo_valido())
{
TTipo_documento & tipo_doc = (TTipo_documento &) tipo();
const TString& tot_doc = tipo_doc.totale_doc();
for (const TFormula_documento* f = tipo_doc.first_formula(); f; f = tipo_doc.succ_formula())
{
TExpr_documento * exp = f->expr();
if (exp != NULL) // Puo' succedere che sia NULL con dati incoerenti
{
if (tot_doc == f->name())
{
TString16 tot_doc_netto(tot_doc);
tot_doc_netto.insert("_");
const TFixed_string netto_def(exp->string());
TExpr_documento netto_exp(netto_def, _numexpr, this);
add_field(new TDocumento_variable_field(tot_doc_netto, netto_exp));
if (netto_def == "IMPONIBILI()+IMPOSTE()")
{
TExpr_documento tot_exp("IMPONIBILI(1)+IMPOSTE(1)", _numexpr, this);
add_field(new TDocumento_variable_field(tot_doc, tot_exp));
}
else
{
TExpr_documento tot_exp(format("%s + _BOLLI(%s)", (const char *) tot_doc_netto,
(const char *) tot_doc_netto), _numexpr, this);
add_field(new TDocumento_variable_field(tot_doc, tot_exp));
}
}
else
{
exp->set_doc(this);
add_field(new TDocumento_variable_field(f->name(), *exp));
}
}
}
}
}
real TDocumento::imponibile(bool spese, int ndec) const
{
real val;
if (physical_rows() > 0)
{
TAssoc_array & table = ((TDocumento *)this)->tabella_iva();
for (TRiepilogo_iva * ri = (TRiepilogo_iva *) table.get(); ri != NULL;
ri = (TRiepilogo_iva *) table.get())
val += ri->imponibile(spese);
if (ndec == AUTO_DECIMALS)
ndec = decimals();
val.round(ndec);
}
return val;
}
void TDocumento::calc_iva_fattura_commerciale()
{
// Calcolo iva per fatture commerciali:
// 1) effettua la sommatoria di tutti i real per ogni elementi di _tabella_iva in un TRiepilogo_iva unico
// 2) azzera _tabella_iva
// 3) scorpora in % a seconda di cio' che e' indicato in configurazione, e mette i nuovi elementi in _tabella_iva
// 4) per ogni nuovo elemento di _tabella_iva, ricalcola la relativa imposta.
TAssoc_array & table = _tabella_iva;
TRiepilogo_iva t;
static TString_array tabella_ripartizione;
const int ndec = decimals();
if (tabella_ripartizione.items() == 0)
{
TConfig cnf(CONFIG_STUDIO, "ve");
for (int k = 1; k <= MAX_IVA_SLICES; k++)
{
TToken_string* tt = new TToken_string();
tt->add(cnf.get("EXCLUDE_PERC", NULL, k));
tt->add(cnf.get("EXCLUDE_IVA", NULL, k));
tabella_ripartizione.add(tt);
}
}
// 1)
table.restart();
for (TRiepilogo_iva * ri = (TRiepilogo_iva *) table.get(); ri != NULL;
ri = (TRiepilogo_iva *) table.get())
{
t.imp() += ri->imp();
t.imp_spese() += ri->imp_spese();
t.imp_spese_row() += ri->imp_spese_row();
t.iva_spese() += ri->iva_spese();
t.iva_sconto() += ri->iva_sconto();
t.sconto_perc() += ri->sconto_perc();
t.sconto_imp() += ri->sconto_imp();
}
// 2)
table.destroy();
// 3)
TArray tda;
tda.add(new TDistrib(t.imp(), ndec));
tda.add(new TDistrib(t.imp_spese(), ndec));
tda.add(new TDistrib(t.imp_spese_row(), ndec));
tda.add(new TDistrib(t.iva_spese(), ndec));
tda.add(new TDistrib(t.iva_sconto(), ndec));
tda.add(new TDistrib(t.sconto_perc(), ndec));
tda.add(new TDistrib(t.sconto_imp(), ndec));
int k;
for (k = 0; k < MAX_IVA_SLICES; k++)
for (int j = 0; j < 7; j++)
{
const real p (tabella_ripartizione.row(k).get(0));
TDistrib& td = (TDistrib&) tda[j];
td.add(p);
}
// 4)
for (k = 0; k < MAX_IVA_SLICES; k++)
{
TString16 cod(tabella_ripartizione.row(k).get(1));
cod.trim();
if (cod.empty())
continue;
const TCodiceIVA civa(cod);
TRiepilogo_iva * rp = (TRiepilogo_iva *) table.objptr(cod);
if (rp == NULL)
{
rp = new TRiepilogo_iva(civa);
table.add(cod, rp);
}
for (int j = 0; j < 7; j++)
{
TDistrib& td = (TDistrib&) tda[j];
const real rr = td.get();
switch (j)
{
case 0:
rp->imp() = rr;
rp->iva() = civa.imposta(rr, ndec);
break;
case 1:
rp->imp_spese() = rr;
break;
case 2:
rp->imp_spese_row() = rr;
break;
case 3:
rp->iva_spese() = rr;
break;
case 4:
rp->iva_sconto() = rr;
break;
case 5:
rp->sconto_perc() = rr;
break;
case 6:
rp->sconto_imp() = rr;
break;
default: break;
}
}
}
}
void TDocumento::update_tabella_iva()
{
const int items = rows();
TAssoc_array & table = _tabella_iva;
if (table.items() > 0 || items == 0)
{
if (items == 0)
table.destroy();
return;
}
real tot_doc;
real tot_sconti;
real tot_sconti_perc;
const bool doc_al_lordo = tipo().calcolo_lordo();
const int ndec = decimals();
const bool fatt_comm = tipo().fattura_commerciale();
TString16 codiva_es;
iva_esente(codiva_es);
for (int i = items; i > 0; i--)
{
const TRiga_documento& r = row(i);
const real imponibile = r.imponibile(doc_al_lordo);
tot_doc += imponibile;
if (r.is_sconto())
{
tot_sconti += imponibile;
if (r.is_sconto_perc())
tot_sconti_perc += imponibile;
}
else
if (!r.is_descrizione())
{
const real imposta = doc_al_lordo ? ZERO :r.imposta(FALSE);
// Aggiorna o aggiunge l'elemento se non esiste
const TCodiceIVA & iva = r.iva();
const TString16 cod(iva.codice());
if (cod.not_empty())
{
TRiepilogo_iva * aliquota = (TRiepilogo_iva *) table.objptr(cod);
if (aliquota == NULL)
{
aliquota = new TRiepilogo_iva(iva);
table.add(cod, aliquota);
}
aliquota->imp() += imponibile;
if (r.is_spese() && iva.tipo().not_empty())
aliquota->imp_spese_row() += imponibile;
aliquota->iva() += imposta;
}
tot_doc += imposta;
}
}
if (table.items() == 0)
return;
if (tot_sconti != ZERO)
{
TGeneric_distrib d(tot_sconti, ndec);
real tot_sconti_imp = tot_sconti - tot_sconti_perc;
table.restart();
TRiepilogo_iva * ri;
for (ri = (TRiepilogo_iva *) table.get(); ri != NULL;
ri = (TRiepilogo_iva *) table.get())
d.add(ri->imp() - ri->imp_spese_row());
table.restart();
for (ri = (TRiepilogo_iva *) table.get(); ri != NULL;
ri = (TRiepilogo_iva *) table.get())
{
const TCodiceIVA & ci = ri->cod_iva();
const real i(d.get());
real & imponibile = ri->imp();
imponibile += i;
TGeneric_distrib s(i, ndec);
s.add(tot_sconti_imp);
s.add(tot_sconti_perc);
ri->sconto_imp() = s.get();
ri->sconto_perc() = s.get();
real & iva = ri->iva();
if (doc_al_lordo)
{
const real imposta(ci.imposta(i, ndec));
TGeneric_distrib iva(imposta, ndec);
iva.add(tot_sconti_imp);
iva.add(tot_sconti_perc);
imponibile += imposta;
ri->sconto_imp() += iva.get();
ri->sconto_perc() += iva.get();
tot_doc += imposta;
}
else
{
const real imposta(ci.imposta(i, ALL_DECIMALS));
iva += imposta;
ri->iva_sconto() = ci.imposta(i, ndec);
tot_doc += imposta;
}
}
}
if (fatt_comm)
calc_iva_fattura_commerciale();
real val = spese_incasso(ALL_DECIMALS, doc_al_lordo ? _lordo : _netto);
if (val != ZERO)
{
const TString16 codiva = codiva_es.not_empty() ? (const TString &) codiva_es : codiva_spese();
TRiepilogo_iva* ri = (TRiepilogo_iva*)table.objptr(codiva);
if (ri == NULL)
{
ri = new TRiepilogo_iva(TCodiceIVA(codiva));
table.add(codiva, ri);
}
ri->imp_spese() += val;
tot_doc += val;
if (!doc_al_lordo)
{
val = spese_incasso(ALL_DECIMALS, _imposta);
ri->iva_spese() += val;
tot_doc += val;
}
}
const real rit = ritenute();
val = bolli(real(tot_doc - rit), ALL_DECIMALS, doc_al_lordo ? _lordo : _netto);
if (val != ZERO)
{
const TString16 codiva = codiva_bolli();
TRiepilogo_iva* ri = (TRiepilogo_iva *) table.objptr(codiva);
if (ri == NULL)
{
ri = new TRiepilogo_iva(TCodiceIVA(codiva));
table.add(codiva, ri);
}
if (!doc_al_lordo)
{
real valiva = bolli(real(tot_doc - rit), ALL_DECIMALS, _imposta);
ri->iva_spese() += valiva;
tot_doc += valiva;
}
ri->imp_spese() += val;
tot_doc += val;
}
// SCORPORO
if (doc_al_lordo)
{
table.restart();
for (TRiepilogo_iva* ri = (TRiepilogo_iva*)table.get(); ri != NULL; ri = (TRiepilogo_iva*)table.get())
{
const TCodiceIVA& iva = ri->cod_iva();
ri->iva() = iva.scorpora(ri->imp(), ndec);
ri->iva_spese() = iva.scorpora(ri->imp_spese(), ndec);
iva.scorpora(ri->imp_spese_row(), ndec);
ri->iva_sconto() = iva.scorpora(ri->sconto_imp(), ndec);
ri->iva_sconto() += iva.scorpora(ri->sconto_perc(), ndec);
}
}
}
real TDocumento::imposta(bool spese, int ndec) const
{
real val = ZERO;
if (physical_rows() > 0)
{
TAssoc_array & table = ((TDocumento *)this)->tabella_iva();
if (ndec == AUTO_DECIMALS)
ndec = decimals();
for (TRiepilogo_iva * ri = (TRiepilogo_iva *) table.get(); ri != NULL;
ri = (TRiepilogo_iva *) table.get())
{
real iva = ri->imposta(spese);
if (ndec == 0)
{
if (iva < ZERO)
iva.floor(ndec);
else
iva.ceil(ndec);
}
else
iva.round(ndec);
val += iva;
}
}
return val;
}
real TDocumento::totale_doc() const
{
const TString16 field(tipo().totale_doc());
if (field.not_empty())
return get_real(field);
else
{
real r = imponibile() + imposta();
const int ndec = decimals();
r += spese_incasso(ndec);
r += bolli(real(r - ritenute()), ndec);
return r;
}
}
real TDocumento::totale_netto() const
{
const TString& field = tipo().totale_netto();
if (field.not_empty())
return get_real(field);
else
return imponibile() + imposta();
}
real TDocumento::basesconto() const
{
const TString& field = tipo().basesconto();
if (field.not_empty())
return get_real(field);
else
return ZERO;
}
real TDocumento::spese() const
{
const TString& field = tipo().spese();
if (field.not_empty())
return get_real(field);
else
return ZERO;
}
real TDocumento::ritenute(const char tipo, bool lordo, int ndec) const
{
real val;
for (int i = rows() ; i > 0; i--)
{
TRiga_documento &r = ((TRiga_documento &) ((TDocumento *)this)->row(i));
val += r.ritenuta(tipo, lordo, ndec);
}
return val;
}
TPagamento& TDocumento::pagamento()
{
const char tipocf = get_char(DOC_TIPOCF);
const long codcf = get_long(DOC_CODCF);
_pag.set_clifo(codcf, tipocf);
TDate data_in = get_date(DOC_DATAINSC);
if (data_in.empty())
data_in = get_date(DOC_DATADOC);
const TString8 codpag(get(DOC_CODPAG));
if (codpag != _pag.code())
{
_pag.set_code(codpag);
_pag.read();
_pag.set_inizio(data_in); // Perche' rispetta rate TRUE?
}
else
{
if (data_in != _pag.get_datadoc())
_pag.set_inizio(data_in); // Perche' rispetta rate TRUE?
}
return _pag;
}
real TDocumento::provvigione(int ndec) const
{
TString16 field = agente().campoprovv();
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
if (field.empty())
field = tipo().totprovv();
real val;
if (field.not_empty())
val = get_real(field);
else
{
if (ndec == AUTO_DECIMALS)
ndec = decimals();
for (int i = rows(); i > 0; i--)
val += ((TRiga_documento &) ((TDocumento *)this)->row(i)).provvigione(ndec);
}
return val;
}
real TDocumento::valore(bool totale, int ndec) const
{
real val;
for (int i=rows(); i>0; i--)
{
TRiga_documento &r = ((TRiga_documento &) ((TDocumento *)this)->row(i));
if (r.is_merce() || r.is_spese() || r.is_prestazione())
val += r.valore(totale, ndec);
}
return val;
}
void TDocumento::put_str(const char* fieldname, const char* val)
{
if (strcmp(fieldname, "TIPODOC") == 0)
{
const TString16 v(val);
if (TRectype::get("TIPODOC") != v)
{
TAuto_variable_rectype::put_str(fieldname, v);
reset_fields(*this);
set_fields(*this);
}
else
dirty_fields();
}
else
if (strcmp(fieldname, "CODCF") == 0)
{
const TString16 v(val);
put("SPESEUPD", TRectype::get("CODCF") == v);
TAuto_variable_rectype::put_str(fieldname, v);
dirty_fields();
}
else
{
TAuto_variable_rectype::put_str(fieldname, val);
dirty_fields();
if (strcmp(fieldname, "SCONTOPERC") == 0)
set_riga_sconto();
}
}
const TString& TDocumento::get_str(const char* fieldname) const
{
if (_dirty_deny && variable_field(fieldname) != NULL)
(bool&) _dirty_deny = FALSE;
return TMultiple_rectype::get_str(fieldname);
}
void TDocumento::zero(const char * fieldname)
{
if (strcmp(fieldname, "TIPODOC") == 0)
reset_fields(*this);
TRectype::zero(fieldname);
dirty_fields();
}
TCli_for & TDocumento::clifor() const
{
const char tipo = tipocf();
const long codice = codcf();
if (_cli_for.empty() || _cli_for.tipo() != tipo || _cli_for.codice() != codice)
((TDocumento *) this)->_cli_for.read(tipo, codice);
return (TCli_for &)_cli_for;
}
TOccasionale & TDocumento::occas() const
{
const TString80 occ_code(cod_occas());
if (_occas.empty() || occ_code != _occas.codice())
{
TLocalisamfile o(LF_OCCAS);
((TDocumento *) this)->_occas.zero();
((TDocumento *) this)->_occas.put(OCC_CFPI, occ_code);
TRectype oc(_occas);
if (((TDocumento *) this)->_occas.read(o) != NOERR)
((TDocumento *) this)->_occas = oc;
}
return (TOccasionale &) _occas;
}
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
const TAgente & TDocumento::agente() const
{
if (_agenti == NULL)
_agenti = new TAgenti_cache;
return _agenti->agente(get(DOC_CODAG));
Sostituito il file vefields.wri con il file vefields.txt Sostituite le tabelle Agenti e Provvigioni con i rispettivi archivi. !!! Devono essere sostituite sui menu e si devono controllare di conseguenza i moduli statistiche di vendita e magazzino !!! Modificato il meccanismo di ricerca delle percentuali di provvigione. Bisogna testare tutte le combinazioni basandosi sulle possibilita' offerte dal nuovo archivio agenti. Per quanto riguarda il valore della provvigione alla percentuale di base viene aggiunta la percentuale reperita con la sequenza alternativa definita sull'archivio agenti. Aggiunto il metodo agente sui documenti. Aggiunto sui tipi documento il flag attivo per le provvigioni di ovvio significato e lo stato a partire dal quale si debbono memorizzare le provvigioni. Aggiunta la funzione TOTPROVV(ndec = AUTO_DECIMALS) per i documenti. Restituisce il valore totale delle provvigioni tenedo conto anche del campo provvigioni definito per l'agente. !!! Deve essere utilizzato solo per avere il valore della provvigione da utilizzare in un calcolo e non per visualizzare o calcolare la provvigione stessa. Aggiunta definizione del campo provvigione della riga (PROVV=....) nei profili riga dei documenti per definire la provvigione della riga quando non e' il default (importo scontato * percentuale di provvigione della riga). Aggiunto il metodo provvigioni alle righe. Aggiunta definizione del campo provvigione del documento (TOTPROVV=....) nei profili documento per definire la provvigione totale quando non e' il default (somma delle provvigioni della riga). Il campo che viene definito come totale delle provvigioni non puo' contenere la funzione TOTPROVV. Aggiunto il metodo provvigione del documento. git-svn-id: svn://10.65.10.50/trunk@5478 c028cbd2-c16b-5b4b-a496-9718f37d4682
1997-10-29 11:08:40 +00:00
}
TDocumento & TDocumento::copy(const TDocumento & d)
{
TMultiple_rectype::operator=((TMultiple_rectype &)d);
reset_fields(*this);
set_fields(*this);
for (int i = physical_rows(); i > 0; i--)
{
TRiga_documento & r = row(i);
r.set_doc(this);
r.set_fields(r);
}
set_riga_sconto();
if (is_fattura())
set_riga_esenzione();
_occas = d.occas();
return *this;
}
TRectype & TDocumento::operator =(const TRectype & r)
{
return TMultiple_rectype::operator=(r);
}
TRectype & TDocumento::operator =(const char * r)
{
return TMultiple_rectype::operator=(r);
}
TRecord_array& TDocumento::body(int logicnum) const
{
const bool reset_data_cons = loaded_rows(logicnum) == 0;
TRecord_array& r = TMultiple_rectype::body(logicnum);
if (reset_data_cons)
{
const TDate datacons(get_date(DOC_DATACONS));
const TString80 codcms(get(DOC_CODCMS));
const TString80 fascms(get(DOC_FASCMS));
const TString80 codcos(get(DOC_CODCOSTO));
for (int i = r.rows(); i > 0; i--)
{
TRectype& rec = r[i];
TRecfield dcons(rec, RDOC_DATACONS);
if (is_ordine() && datacons == dcons)
dcons = "";
TRecfield ccms(rec, RDOC_CODCMS);
TRecfield fcms(rec, RDOC_FASCMS);
TRecfield ccos(rec, RDOC_CODCOSTO);
if (codcms == ccms && fascms == fcms && codcos == ccos)
{
ccms = "";
fcms = "";
ccos = "";
}
}
}
return r;
}
void TDocumento::update_spese_aut(TString_array & spese_aut, bool preserve_old, TSheet_field * sh)
{
const bool updated = get_bool("SPESEUPD");
if (updated)
return;
const bool interactive = sh != NULL;
if (tipo().spese_aut())
{
const int nrows = physical_rows();
int i;
for (i = nrows; i > 0; i--)
{
TRiga_documento & r = row(i);
bool tipo_spese = r.get("GENTIPO").empty();
if (r.tipo().tipo() == RIGA_SPESEDOC && r.is_generata() && tipo_spese)
{
if (preserve_old)
return;
destroy_row(i, TRUE);
if (interactive)
sh->destroy(i - 1);
}
}
TString16 cod_iva_cli;
const int nspese = spese_aut.items();
if (nspese > 0)
{
TLocalisamfile cfven(LF_CFVEN);
TSpesa_prest sp;
cfven.put("TIPOCF", get("TIPOCF"));
cfven.put("CODCF", get("CODCF"));
if (cfven.read() == NOERR)
cod_iva_cli = cfven.get("ASSFIS");
for (i = 0; i < nspese; i++)
{
const TString & s = spese_aut.row(i);
if (sp.read(s) != NOERR)
message_box("Codice spesa %s assente", (const char *) s);
else
{
TString16 tipo(sp.tipo_riga());
TRiga_documento & riga = new_row(tipo);
riga.put("CODART", s);
riga.generata();
riga.put("DESCR", sp.descrizione());
switch (sp.tipo())
{
case 'Q':
{
real qta = sp.qta();
if (qta == ZERO)
qta = 1.0;
riga.put("QTA", qta);
}
case 'V':
{
const real cambio = get_real(DOC_CAMBIO);
const TString16 valuta = get(DOC_CODVAL);
const exchange_type controeuro = get_bool(DOC_CONTROEURO) ? _exchange_contro : _exchange_base;
real prezzo = sp.prezzo();
sppr_calc(sp, valuta, cambio, prezzo, controeuro);
riga.put("PREZZO", prezzo);
riga.put("UMQTA", sp.um());
}
break;
case 'P':
default:
riga.put("QTA", sp.perc());
break;
}
if (cod_iva_cli.empty())
riga.put("CODIVA", sp.cod_iva());
else
riga.put("CODIVA", cod_iva_cli);
if (interactive)
{
const int nrow = sh->insert(-1, FALSE);
riga.autoload(*sh);
sh->check_row(nrow);
}
}
}
}
}
put("SPESEUPD", true);
}
real TDocumento::calc_conai_qta(int type)
{
const char * const __conai_art_names[] = {"CONACC", "CONALL", "CONCAR", "CONPLA", "CONLEG", "CONVET"};
const char * const __conai_cf_names[] = {"ESACC", "ESALL", "ESCAR", "ESPLA", "ESLEG", "ESVET"};
const real perc_esenz = clifor().vendite().get_real(__conai_cf_names[type]);
real qta = ZERO;
if (perc_esenz < 100.0)
{
const int nrows = physical_rows();
for (int i = nrows; i > 0; i--)
{
TRiga_documento & r = row(i);
TArticolo_giacenza * art = r.articolo();
if (art != NULL)
{
const real row_qta = r.get_real(RDOC_QTA);
qta += row_qta*art->get_real(__conai_art_names[type]);
}
}
if (qta > ZERO)
{
// qta *= (1 - perc_esenz/100.0);
qta = qta * (100 - perc_esenz) / 100.0; // More precise!
}
}
return qta;
}
void TDocumento::update_conai()
{
if (tipo().add_conai())
{
const bool cli_add_conai = clifor().vendite().get_bool("ADDCONAI");
const char* conai_cod[6] = { "CODACC", "CODALL", "CODCAR", "CODPLA", "CODLEG", "CODVET" };
const char* conai_mat[6] = { "Acciaio", "Alluminio", "Carta", "Plastica", "Legno", "Vetro" };
TString_array conai_sp(6); // Codici spesa conai
{
TConfig c(CONFIG_DITTA, "ve");
for (int i = 0; i < 6; i++)
conai_sp.add(c.get(conai_cod[i]));
}
bool updated[6] = {FALSE,FALSE,FALSE,FALSE,FALSE,FALSE};
const int nrows = physical_rows();
int i;
for (i = nrows; i > 0; i--)
{
TRiga_documento& r = row(i);
const bool tipo_conai = r.get_char("GENTIPO") == 'C';
// Elimina righe generate
if (tipo_conai && r.tipo().tipo() == RIGA_SPESEDOC && r.is_generata())
{
const TString16 cod(r.get("CODART"));
const int pos = conai_sp.find(cod);
if (pos >= 0)
{
if (cli_add_conai)
{
real qta = calc_conai_qta(pos);
if (qta > ZERO)
r.put("QTA", qta);
else
destroy_row(i, TRUE);
}
else
destroy_row(i, TRUE);
updated[pos] = TRUE;
}
}
}
// Genera nuove righe
if (cli_add_conai)
{
const TString16 cod_iva_cli = clifor().vendite().get("ASSFIS");
TSpesa_prest sp;
for (i = 0; i < 6; i++)
{
if (!updated[i])
{
const real qta = calc_conai_qta(i);
if (qta > ZERO)
{
const TString & s = conai_sp.row(i);
if (sp.read(s) != NOERR)
message_box("Il codice spesa CONAI %s specificato nei parametri ditta e' assente: '%s'",
conai_mat[i], (const char*)s);
else
{
TString16 tipo(sp.tipo_riga());
TRiga_documento & riga = new_row(tipo);
riga.put("CODART", s);
riga.generata();
riga.put("GENTIPO", "C");
riga.put("DESCR", sp.descrizione());
riga.put("QTA", qta);
const real cambio = get_real(DOC_CAMBIO);
const TString16 valuta = get(DOC_CODVAL);
const bool controeuro = get_bool(DOC_CONTROEURO);
real prezzo = sp.prezzo();
sppr_calc(sp, valuta, cambio, prezzo, controeuro ? _exchange_contro : _exchange_base);
riga.put("PREZZO", prezzo);
riga.put("UMQTA", sp.um());
if (cod_iva_cli.empty())
riga.put("CODIVA", sp.cod_iva());
else
riga.put("CODIVA", cod_iva_cli);
}
}
}
}
}
}
}
bool TDocumento::is_evaso() const
{
bool ok = is_ordine() || is_bolla() || is_generic();
for (int r = 1; ok && r <= physical_rows(); r++)
{
const TRiga_documento& riga = physical_row(r);
if (riga.is_evadibile())
ok = riga.is_evasa();
}
return ok;
}
bool TDocumento::is_nota_credito() const
{
bool swap = FALSE;
// Controlla prima l'esistenza del flag nota-credito sul tipo documento;
// se non e' settato controlla la causale
if (tipo().nota_credito())
swap = TRUE;
else
{
const TString16 codcaus(tipo().causale());
if (codcaus.not_empty())
{
TLocalisamfile caus(LF_CAUSALI);
TLocalisamfile rcaus(LF_RCAUSALI);
TCausale c(codcaus, data().year());
const char sez = c.sezione_clifo();
swap = ((c.reg().iva() == iva_vendite) ^ (sez == 'D'));
}
}
return swap;
}
TCurrency_documento::TCurrency_documento(const real& num, const TDocumento & doc, bool price)
: TCurrency(ZERO, "", ZERO, _exchange_base, price)
{
const TString16 val(doc.get(DOC_CODVAL));
const bool controeuro = doc.get_bool(DOC_CONTROEURO);
force_value(val, doc.get_real(DOC_CAMBIO), controeuro ? _exchange_contro : _exchange_base);
set_num(num);
}
int TDocumento::set_row_ids()
{
const int phrw = physical_rows();
long maxid = 0L;
int first_needed = 0, r;
for (r = 1; r <= phrw; r++)
{
const TRiga_documento& row = physical_row(r);
const long id = row.get_long(RDOC_IDRIGA);
if (id > maxid)
maxid = id;
else
{
if (first_needed == 0)
first_needed = r;
}
}
if (first_needed > 0)
{
for (r = first_needed; r <= phrw; r++)
{
TRiga_documento& row = (TRiga_documento&)physical_row(r);
const long id = row.get_long(RDOC_IDRIGA);
if (id <= 0)
row.put(RDOC_IDRIGA, ++maxid);
}
}
return phrw;
}
const TRiga_documento* TDocumento::get_row_id(long id) const
{
for (int r = physical_rows(); r > 0; r--)
{
const TRiga_documento& row = physical_row(r);
if (row.get_long(RDOC_IDRIGA) == id)
return &row;
}
return NULL;
}