campo-sirio/sv/sv1100.cpp
guy dc50349bd6 Eliminati riferimenti a campo obsoleto CONTROEURO
git-svn-id: svn://10.65.10.50/branches/R_10_00@22633 c028cbd2-c16b-5b4b-a496-9718f37d4682
2012-04-10 07:50:54 +00:00

1476 lines
38 KiB
C++
Executable File
Raw Blame History

#include <applicat.h>
#include <printer.h>
#include <progind.h>
#include <urldefid.h>
#include "../pr/agenti.h"
#include "../sc/scselect.h"
#include "../ve/velib.h"
#include <doc.h>
#include "sv1.h"
#include "sv1100a.h"
class TSchede_mask : public TSelection_mask
{
void init_sheet(short id);
void ini2sheet(short id);
void sheet2ini(short id);
protected:
static bool date_handler(TMask_field& f, KEY k);
static bool num_handler(TMask_field& f, KEY k);
static bool save_handler(TMask_field& f, KEY k);
static bool sheet_notify(TSheet_field& s, int row, KEY k);
static bool fieldname_handler(TMask_field& f, KEY k);
static bool valuta_handler(TMask_field& f, KEY k);
static bool realfield_handler(TMask_field& f, KEY k);
static bool cambio_handler(TMask_field& f, KEY k);
public:
void mask2ini();
void ini2mask();
TSchede_mask();
virtual ~TSchede_mask() { }
};
bool TSchede_mask::date_handler(TMask_field& f, KEY k)
{
bool ok = true;
if (f.to_check(k))
{
TMask& m = f.mask();
const TDate fd(m.get(F_FROMDATE));
const TDate td(m.get(F_TODATE));
if (td.ok() && td < fd)
ok = f.error_box(TR("La data finale deve seguire quella iniziale"));
}
return ok;
}
bool TSchede_mask::num_handler(TMask_field& f, KEY k)
{
bool ok = true;
if (f.to_check(k))
{
TMask& m = f.mask();
const TString& fn = m.get(F_FROMNUM);
const TString& tn = m.get(F_TONUM);
if (tn.not_empty() && tn < fn)
ok = f.error_box(TR("La numerazione finale deve seguire quella iniziale"));
}
return ok;
}
bool TSchede_mask::valuta_handler(TMask_field& f, KEY key)
{
if (key == K_TAB && f.to_check(key, true))
{
TMask& m = f.mask();
const TString& val = f.get();
const bool full = val.not_empty() && val != TCurrency::get_firm_val();
if (full)
{
TEdit_field& dc = m.efield(F_DATACAMBIO);
if (dc.empty()) // Inizializza data cambio se assente
{
const TDate oggi(TODAY);
dc.set(oggi.string());
}
if (f.focusdirty())
{
dc.set_dirty();
dc.check(RUNNING_CHECK); // Forza ricerca cambio
if (m.get(F_CAMBIO).empty())
{
TCursor& cur = *dc.browse()->cursor();
if (cur.items() == 0) // Uso cambio standard
{
const TRectype& rec = cache().get("%VAL", val);
dc.set(rec.get("D0"));
m.set(F_CAMBIO, rec.get("S4"));
m.set(F_CONTROEURO, rec.get("B1"));
}
}
}
}
else
{
m.reset(F_DATACAMBIO);
m.reset(F_CAMBIO);
m.reset(F_CONTROEURO);
}
}
return true;
}
bool TSchede_mask::save_handler(TMask_field& f, KEY k)
{
if (k == K_SPACE)
{
TSchede_mask& m = (TSchede_mask&)f.mask();
m.mask2ini();
}
return true;
}
bool TSchede_mask::fieldname_handler(TMask_field& f, KEY k)
{
if (f.to_check(k))
{
TSchede_mask& m = (TSchede_mask&)f.mask();
TEdit_field& head = m.efield(S_HEAD);
if (head.empty())
{
TParagraph_string para(m.get(S_DESCR), head.size());
head.set(para.get(0));
}
}
return true;
}
bool TSchede_mask::realfield_handler(TMask_field& f, KEY k)
{
if (k == K_F9)
{
TMask& m = f.mask();
const TSheet_field& s = *m.get_sheet();
TRelation rel(s.dlg() == F_SINTETICA ? LF_DOC : LF_RIGHEDOC);
TRelation_description rd(rel);
if (rd.choose_field(f.get()))
{
f.set(rd.field_name());
TEdit_field& head = m.efield(S_HEAD);
TParagraph_string para(rd.field_desc(), head.size());
head.set(para.get(0));
m.set(S_DESCR, rd.field_desc());
if (rd.field_type() == _realfld)
{
const int decimals = rel.curr().ndec(rd.field_name());
const int length = rel.curr().length(rd.field_name());
m.set(S_IMPORTO, (decimals <= 3 && length >= 6)? "X" : "");
}
else
return f.error_box(TR("E' necessario selezionare un campo numerico."));
}
}
return true;
}
bool TSchede_mask::sheet_notify(TSheet_field& s, int row, KEY k)
{
bool ok = true;
switch(k)
{
case K_INS:
ok = s.items() < 8; // Posso aggiungere al massimo otto colonne di stampa
break;
case K_CTRL+K_INS:
s.row(row) = "F"; // Proponi una formula
break;
default:
break;
}
return ok;
}
void TSchede_mask::sheet2ini(short id)
{
TSheet_field& sheet = sfield(id);
TString_array& arr = sheet.rows_array();
const char* field = id == F_SINTETICA ? "SynField" : "DetField";
const char* head = id == F_SINTETICA ? "SynHead" : "DetHead";
TConfig ini(CONFIG_STUDIO, "sv1100");
for (int r = arr.last(); r >= 0; r--)
{
TToken_string& row = arr.row(r);
ini.set(field, row.get(1), NULL, true, r);
ini.set(head, row.get(), NULL, true, r);
}
ini.remove(field, arr.items());
ini.remove(head, arr.items());
}
void TSchede_mask::ini2sheet(short id)
{
TSheet_field& sheet = sfield(id);
const char* field = id == F_SINTETICA ? "SynField" : "DetField";
const char* head = id == F_SINTETICA ? "SynHead" : "DetHead";
TRelation rel(id == F_SINTETICA ? LF_DOC : LF_RIGHEDOC);
const TRectype& rec = rel.curr();
TRelation_description rd(rel);
TConfig ini(CONFIG_STUDIO, "sv1100");
for (int r = 0; ; r++)
{
TString16 str = ini.get(field, NULL, r);
if (str.not_empty())
{
TToken_string& row = sheet.row(r);
row = rec.exist(str) ? "C" : "F";
row.add(str);
row.add(ini.get(head, NULL, r));
if (row[0] == 'C')
{
row.add(rd.get_field_description(str));
if (rec.type(str) == _realfld)
row.add(rec.ndec(str) <= 3 ? "X" : "");
}
else
sheet.check_row(r);
}
else
break;
}
}
void TSchede_mask::mask2ini()
{
sheet2ini(F_SINTETICA);
sheet2ini(F_DETTAGLIATA);
}
void TSchede_mask::ini2mask()
{
ini2sheet(F_SINTETICA);
ini2sheet(F_DETTAGLIATA);
}
void TSchede_mask::init_sheet(short id)
{
TSheet_field& sheet = sfield(id);
sheet.set_notify(sheet_notify);
TMask& sm = sheet.sheet_mask();
sm.set_handler(S_FIELD, fieldname_handler);
sm.set_handler(S_REALFIELD, realfield_handler);
}
TSchede_mask::TSchede_mask()
: TSelection_mask("sv1100a")
{
set_handler(F_TODATE, date_handler);
set_handler(F_TONUM, num_handler);
set_handler(F_VALUTA, valuta_handler);
set_handler(DLG_SAVEREC, save_handler);
init_sheet(F_SINTETICA);
init_sheet(F_DETTAGLIATA);
ini2mask();
}
///////////////////////////////////////////////////////////
// TSchede_form
///////////////////////////////////////////////////////////
class TSchede_form : public TForm
{
public:
void init(const TSheet_field& sheet);
void init_pictures(const TMask& msk);
TSchede_form(const char* n);
virtual ~TSchede_form() { }
};
TSchede_form::TSchede_form(const char* n)
: TForm(n)
{
}
void TSchede_form::init(const TSheet_field& sheet)
{
TPrint_section& body = section('B', odd_page);
TString_array& arr = sheet.rows_array();
TString80 str;
bool on = true;
for (word r = 3; r < body.fields(); r++)
{
const int riga = r-3;
if (on)
{
if (riga < arr.items())
{
str = arr.row(riga).get(1);
on = str.not_empty();
}
else
on = false;
}
TForm_item& item = body.field(r);
if (!item.is_section())
{
item.show(on);
if (on)
{
str = arr.row(riga).get(2);
if (str.blank())
str = arr.row(riga).get(1);
item.set_col_head(str);
}
}
}
const TPrint_section& head = section('H', odd_page);
const TPrint_section& foot = section('F', odd_page);
const int hh = head.height();
const int fh = foot.height();
const int fl = printer().formlen();
int rows[4]; // Righe orizzontali
rows[0] = hh-2; // Terzultima riga della testata
rows[1] = hh; // Ultima riga della testata
rows[2] = fl-fh+1; // Prima riga del footer
rows[3] = 0;
genera_fincatura(odd_page, rows[0], rows[2], rows);
TForm::genera_intestazioni(odd_page, hh-1);
}
void TSchede_form::init_pictures(const TMask& msk)
{
const TPrint_section& head = section('H', odd_page);
const int hh = head.height();
TForm::genera_intestazioni(odd_page, hh-1);
const char tipo_stampa = msk.get(F_TIPO)[0];
TSheet_field& sheet = msk.sfield(tipo_stampa == 'D' ? F_DETTAGLIATA : F_SINTETICA);
const int imppos = sheet.cid2index(S_IMPORTO);
const int rfpos = sheet.cid2index(S_REALFIELD);
const int ftpos = sheet.cid2index(S_FIELDTYPE);
TPrint_section& body = section('B', odd_page);
const int campi = sheet.items()+2;
const TCurrency valuta(ZERO, msk.get(F_VALUTA));
TRectype rec(tipo_stampa == 'D' ? LF_RIGHEDOC : LF_DOC);
TString16 pic;
for (int c = 0; c < campi; c++)
{
TForm_item& fi = body.find_field(FF_FIRSTCOLUMN+c);
bool importo = true;
if (c > 1)
importo = sheet.row(c-2).get_char(imppos) > ' ';
if (importo)
{
pic.format(".%d", valuta.decimals());
fi.set_picture(pic);
}
else
{
if (c > 1 && sheet.row(c-2).get_char(ftpos) == 'C')
{
pic.format(".%d",rec.ndec(sheet.row(c-2).get(rfpos)));
fi.set_picture(pic);
}
}
}
}
///////////////////////////////////////////////////////////
// Main app
///////////////////////////////////////////////////////////
class TStampa_schede : public TSkeleton_application
{
char _clifo; // <C>lienti o <F>ornitori
char _tipo; // <D>ettagliata o <S>intetica
char _sort; // <F>attura o <A>rticolo
char _prov; // <P>rovvisori o <D>efinitivi
bool _peragenti; // Stampa per agenti
bool _perageart; // Stampa per agenti ma ordinata per Articolo, Cliente, documento
bool _provvart; // Stampa solo righe articolo con provvigione
TString _curagente; // Codice e descrizione agente corrente
TDate _fromdate, _todate; // Date limite
TString _fromnum, _tonum; // Numerazioni limite
TString _tipodoc; // Tipo documento limite
TArray _totali; // Totali complessivi
TArray _totriga; // Totali di riga
TArray _totage; // Totali per agente
long _progressivo; // Numero progressivo di record per file di stampa
TString _lastkey; // Ultima chiave del file di stampa temporaneo
TSchede_mask* _mask; // Mask di stampa
TSchede_form* _form; // Form di stampa
protected:
virtual void main_loop();
virtual bool create();
virtual bool destroy();
protected:
void put_real(TRectype& tab, int index, real val, bool importo, const TExchange& fc, const TExchange& tc);
void fill_key(TRectype& tab, const TDocumento& doc, const bool ageart = false);
void fill_key(TRectype& tab, const TRiga_documento& rdoc, const bool ageart = false);
static bool filtra_doc_per_stat(const TRelation* rel);
public:
// stampa un documento (stampa sintetica)
bool fill_doc(TRectype& tab, const TDocumento& doc);
// stampa una riga documento (stampa dettagliata)
bool fill_rdoc(TRectype& tab, const TRiga_documento& rdoc, const bool ageart = false);
void update_totriga(const TRectype& tab);
void update_totage(const TRectype& tab);
void fill_totriga(TRectype& tab);
void fill_tot(TRectype& tab);
void fill_totage(TRectype& tab);
bool fill_codart(TRectype& tab);
bool fill_codcli(TRectype& tab);
bool write_tab(TLocalisamfile& tab) const;
bool write_totali_per_articolo(TLocalisamfile& tab);
bool write_artcli_descrizioni(TLocalisamfile& tab);
bool stampa_clienti() const { return _clifo == 'C'; }
bool stampa_fornitori() const { return _clifo == 'F'; }
bool stampa_sintetica() const { return _tipo == 'S'; }
bool stampa_dettagliata() const { return _tipo == 'D'; }
bool stampa_per_articolo() const { return _sort == 'A'; }
bool stampa_per_documento() const { return _sort == 'D'; }
bool stampa_per_agente() const { return _peragenti; }
bool stampa_per_ageart() const { return _perageart; }
long clifo2index(TCursor_sheet& clifosheet, long codcf);
bool raggruppa_articoli(TCursor& cur, TProgind* pi, bool last_clifo);
bool stampa_clifo(TCursor& cur, const TString& ragsoc, bool last_clifo);
bool stampa_selezione(TCursor& clifocur, const TSheet& clifosheet, const TString& filter);
};
void TStampa_schede::put_real(TRectype& tab, int index, real val, bool importo,
const TExchange& fc, const TExchange& tc)
{
char erre[4]; sprintf(erre, "R%d", index);
if (importo)
{
TCurrency cur(val, fc);
cur.change_value(tc);
val = cur.get_num();
}
tab.put(erre, val);
// Se non <20> un importo, non va totalizzato (ad esempio le quantita...)
if (importo)
{
real* r = (real*)_totali.objptr(index);
if (r == NULL)
_totali.add(val, index);
else
*r += val;
}
}
void TStampa_schede::fill_key(TRectype& tab, const TDocumento& doc, const bool ageart)
{
tab.zero();
tab.put("COD", "PRN");
const TCli_for& clifo = doc.clifor();
tab.put("S8", clifo.tipo());
tab.put("I8", clifo.codice());
if (ageart)
tab.put("S4", doc.get("CODAG"));
TString16 str;
TString80 key;
if (ageart)
key.format("%c%7ld", clifo.tipo(), clifo.codice());
key << doc.data().string(ANSI);
str = doc.numerazione(); str.left_just(4);
key << str;
str.format("%4d", doc.numero());
key << str;
tab.put("S0", key);
tab.put("CODTAB", ++_progressivo);
}
void TStampa_schede::fill_key(TRectype& tab, const TRiga_documento& rdoc, const bool ageart)
{
fill_key(tab, rdoc.doc(), ageart);
_lastkey = tab.get("S0");
_lastkey.left_just(20);
if (stampa_per_articolo() || ageart)
{
TString80 str = rdoc.get(RDOC_CODART);
str.left_just(20);
_lastkey.insert(str, 0);
}
TString16 numero;
numero.format("%4d", rdoc.numero());
_lastkey << numero;
tab.put("S0", _lastkey);
}
bool TStampa_schede::fill_doc(TRectype& tab, const TDocumento& doc)
{
if (stampa_dettagliata())
return false;
const TTipo_documento& tipo = doc.tipo();
if (!tipo.statistiche()) // documento non abilitato per le statistiche
return false;
// Codice valuta del documento
const TExchange fc(doc.head());
// Codice valuta di stampa
const TString& codval = _mask->get(F_VALUTA);
const real cambio = _mask->get(F_CAMBIO);
const TExchange tc(codval, cambio);
fill_key(tab, doc);
TString descr(80);
const TCodice_numerazione& num = doc.codice_numerazione();
descr << tipo.descrizione() << ' ';
descr << num.prefisso();
descr << doc.numero();
descr << num.postfisso();
descr << " del " << doc.data();
tab.put("S1", descr);
const bool is_nota_credito = doc.tipo().nota_credito();
real bs = doc.basesconto();
real td = doc.totale_doc();
if (is_nota_credito)
{
bs = -bs;
td = -td;
}
put_real(tab, 0, bs, true, fc, tc);
put_real(tab, 1, td, true, fc, tc);
TSheet_field& sheet = _mask->sfield(F_SINTETICA);
const int fldpos = sheet.cid2index(S_FIELD);
const int imppos = sheet.cid2index(S_IMPORTO);
TString_array& arr = sheet.rows_array();
TString16 src;
for (int r = 0; r < arr.items(); r++)
{
TToken_string& row = arr.row(r);
src = row.get(fldpos);
if (src.blank())
break;
const bool importo = row.get_char(imppos) > ' ';
real val = doc.get(src);
if (is_nota_credito)
val = -val;
put_real(tab, r+2, val, importo, fc, tc);
}
return true;
}
bool TStampa_schede::fill_rdoc(TRectype& tab, const TRiga_documento& rdoc, const bool ageart)
{
if (stampa_sintetica())
return false;
switch(rdoc.tipo().tipo())
{
case RIGA_MERCE : break;
case RIGA_OMAGGI : break;
case RIGA_PRESTAZIONI: break;
default : return false;
}
const TDocumento& doc = rdoc.doc();
const TTipo_documento& tipo = doc.tipo();
if (!tipo.statistiche()) // documento non abilitato per le statistiche
return false;
// Codice valuta del documento
const TExchange fc(doc.head());
// Codice valuta di stampa
const TString& codval = _mask->get(F_VALUTA);
const real cambio = _mask->get(F_CAMBIO);
const TExchange tc(codval, cambio);
fill_key(tab, rdoc, ageart);
TString descr(80);
if (ageart)
{
descr << TR("*** Doc.") << doc.numerazione();
descr << '/' << doc.numero();
descr << TR(" del ") << doc.data();
}
else
{
if (stampa_per_articolo())
{
descr << doc.numerazione();
descr << ' ' << doc.numero();
descr << "," << doc.data();
descr << ':' << rdoc.get(RDOC_DESCR);
} else {
descr << rdoc.get(RDOC_CODART) << ' ';
descr << rdoc.get(RDOC_DESCR);
}
}
descr.cut(50);
tab.put("S1", descr);
const bool is_nota_credito = doc.tipo().nota_credito();
real ins = rdoc.importo(true, false);
real ils = rdoc.importo(true, true);
if (is_nota_credito)
{
ins = -ins;
ils = -ils;
}
put_real(tab, 0, ins, true, fc, tc); // importo netto scontato
put_real(tab, 1, ils, true, fc, tc); // importo lordo scontato
TSheet_field& sheet = _mask->sfield(F_DETTAGLIATA);
TString_array& arr = sheet.rows_array();
const int fldpos = sheet.cid2index(S_FIELD);
const int imppos = sheet.cid2index(S_IMPORTO);
TString16 src;
for (int r = 0; r < arr.items(); r++)
{
TToken_string& row = arr.row(r);
src = row.get(fldpos);
if (src.blank())
break;
const bool importo = row.get_char(imppos) > ' ';
real val = rdoc.get(src);
if (is_nota_credito)
val = -val;
put_real(tab, r+2, val, importo, fc, tc);
}
return true;
}
void TStampa_schede::update_totriga(const TRectype& tab)
{
char erre[4];
for (int r = _totali.last(); r >= 0; r--)
{
sprintf(erre, "R%d", r);
const real val(tab.get(erre));
real* tot = (real*)_totriga.objptr(r);
if (tot == NULL)
_totriga.add(val, r);
else
*tot += val;
}
}
void TStampa_schede::fill_totriga(TRectype& tab)
{
TString80 descr;
tab.zero();
tab.put("COD", "PRN");
tab.put("CODTAB", ++_progressivo);
_lastkey.overwrite("9999", _lastkey.len()-4);
tab.put("S0", _lastkey);
if (stampa_per_articolo())
{
descr= "Totale articolo " ;
descr << _lastkey.left(20);
} else {
TDate ddoc;
ddoc.set_year(atoi(_lastkey.left(4)));
ddoc.set_month(atoi(_lastkey.mid(4,2)));
ddoc.set_day(atoi(_lastkey.mid(6,2)));
descr << TR("Totale documento ") << _lastkey.mid(8,4) ;
descr << ' ' << atoi(_lastkey.mid(12,4));
descr << TR(" del ") << ddoc;
}
tab.put("S1", descr);
tab.put("B8", true); // Riga totale
TSheet_field& sheet = _mask->sfield(stampa_dettagliata() ? F_DETTAGLIATA : F_SINTETICA);
TString_array& arr = sheet.rows_array();
const int imppos = sheet.cid2index(S_IMPORTO);
for (int r = _totriga.last(); r >= 0; r--)
{
const bool importo = r > 1 ? arr.row(r-2).get_char(imppos) > ' ' : true;
char erre[4]; sprintf(erre, "R%d", r);
tab.put(erre, importo ? (real&)_totriga[r] : ZERO);
}
}
bool TStampa_schede::fill_codart(TRectype& tab)
{
const TString codart = _lastkey.left(20);
if (codart == "zzzzzzzz")
return false;
const TString codag = tab.get("S4");
tab.zero();
tab.put("COD", "PRN");
tab.put("CODTAB", ++_progressivo);
tab.put("S0", codart);
TString s;
s << "@B" << codart;
s.trim();
s << ' ' << cache().get(LF_ANAMAG, codart, "DESCR");
tab.put("S1", s);
tab.put("S4", codag); // Riporta il codice agente
return true;
}
bool TStampa_schede::fill_codcli(TRectype& tab)
{
TString s = _lastkey.left(28); // CODART + TIPOCF + CODCF
const long c = atol(s.right(7));
if (c <= 0)
return false;
const char t = s[20];
TLocalisamfile& clifo = _form->relation()->lfile(LF_CLIFO);
const TString codag = tab.get("S4");
tab.zero();
tab.put("COD", "PRN");
tab.put("CODTAB", ++_progressivo);
tab.put("S0", s);
clifo.put("TIPOCF", t); clifo.put("CODCF", c);
s = t == 'C' ? TR("Cliente ") : TR("Fornitore ") ;
s << c << " ";
if (clifo.read() == NOERR)
s << clifo.get("RAGSOC");
s.strip_double_spaces();
tab.put("S1", s);
tab.put("S4", codag); // Riporta il codice agente
return true;
}
void TStampa_schede::fill_tot(TRectype& tab)
{
tab.zero();
tab.put("COD", "PRN");
tab.put("CODTAB", ++_progressivo);
tab.put("S0", "yyyyyyyy"); // Si assicura che sia l'ultima prima dell'agente
tab.put("S1", "Totale");
tab.put("B8", true); // Riga totale
for (int r = _totali.last(); r >= 0; r--)
{
const real* t = (const real*)_totali.objptr(r);
char erre[4]; sprintf(erre, "R%d", r);
tab.put(erre, t == NULL ? ZERO : *t);
}
}
bool TStampa_schede::write_tab(TLocalisamfile& tab) const
{
int err = tab.write();
if (err != NOERR)
error_box(FR("Errore %d durante la scrittura sul file temporaneo"), err);
return err == NOERR;
}
bool TStampa_schede::write_totali_per_articolo(TLocalisamfile& tab)
{
bool ok = true;
TRectype& curtab = tab.curr();
const TRecfield key(curtab, "S0");
_lastkey.cut(0);
_totriga.destroy();
for (int err = tab.first(); err == NOERR && ok; err = tab.next())
{
if (_lastkey.not_empty() && _lastkey.compare((const char*)key, 20) != 0)
{
const TRecnotype pos = tab.recno();
fill_totriga(curtab);
ok = write_tab(tab);
tab.readat(pos);
_totriga.destroy();
}
_lastkey = (const char*)key;
update_totriga(curtab);
}
if (ok && _lastkey.not_empty())
{
fill_totriga(curtab);
ok = write_tab(tab);
}
return ok;
}
bool TStampa_schede::write_artcli_descrizioni(TLocalisamfile& tab)
{
bool ok = true;
TRectype& curtab = tab.curr();
const TRecfield key(curtab, "S0");
const TRecfield art(curtab, "S0", 0, 19);
TString last_art;
_lastkey = "";
for (int err = tab.first(); err == NOERR && ok; err = tab.next())
{
if (_lastkey.not_empty())
if (_lastkey.compare((const char*)key, 28) != 0) // Cambio articolo o cliente
{
const TRecnotype pos = tab.recno();
if (last_art != (const char*)art)
{
if (fill_codart(curtab))
ok = write_tab(tab);
}
// <20> per forza un cambio codcf
if (fill_codcli(curtab))
ok = write_tab(tab);
tab.put("S0", _lastkey);
if (tab.read() == NOERR)
{
tab.put("B8", true);
tab.rewrite();
}
tab.readat(pos);
}
_lastkey = (const char*)key;
last_art = (const char*)art;
}
if (ok && _lastkey.not_empty())
{
tab.put("B8",true); tab.rewrite();
if (fill_codart(curtab))
ok = write_tab(tab);
if (fill_codcli(curtab))
ok = write_tab(tab);
}
return ok;
}
void TStampa_schede::update_totage(const TRectype& tab)
{
char erre[4];
for (int r = _totali.last(); r >= 0; r--)
{
sprintf(erre, "R%d", r);
const real val(tab.get(erre));
real* tot = (real*)_totage.objptr(r);
if (tot == NULL)
_totage.add(val, r);
else
*tot += val;
}
}
void TStampa_schede::fill_totage(TRectype& tab)
{
tab.zero();
tab.put("COD", "PRN");
tab.put("CODTAB", ++_progressivo);
TString80 descr;
descr << TR("Totale Agente ") << _curagente;
descr.cut(50);
tab.put("S0", "zzzzzzzz"); // Mi assicuro che sia l'ultima riga
tab.put("S1", descr);
tab.put("S4", _curagente.left(5));
tab.put("B8", true); // Riga totale
TSheet_field& sheet = _mask->sfield(stampa_dettagliata() || stampa_per_ageart() ? F_DETTAGLIATA : F_SINTETICA);
TString_array& arr = sheet.rows_array();
const int imppos = sheet.cid2index(S_IMPORTO);
for (int r = _totage.last(); r >= 0; r--)
{
const bool importo = r > 1 ? arr.row(r-2).get_char(imppos) > ' ' : true;
char erre[4]; sprintf(erre, "R%d", r);
tab.put(erre, importo ? (real&)_totage[r] : ZERO);
}
}
bool TStampa_schede::raggruppa_articoli(TCursor& cur, TProgind* pi, bool last_clifo)
{
const long items = cur.items();
cur.file().set_curr(new TDocumento);
TDocumento& doc = (TDocumento&)cur.file().curr();
TLocalisamfile& tab = _form->relation()->lfile();
TRectype& curtab = tab.curr();
bool can_print = true;
bool has_money = false;
// Scorre i documenti del cliente corrente
for (cur = 0; cur.pos() < items && can_print; ++cur)
{
if (pi->iscancelled())
{
can_print = false;
break;
}
// Scorre le righe del documento corrente
for (int r = doc.physical_rows(); r > 0 && can_print; r--)
{
const TRiga_documento& rdoc = doc[r];
if (rdoc.is_articolo())
{
bool fill = true;
if (_provvart)
fill = !rdoc.provvigione().is_zero();
if (fill && fill_rdoc(curtab, rdoc, true))
{
can_print = write_tab(tab);
if (can_print)
{
update_totage(curtab);
has_money = true;
}
}
}
}
}
if (can_print && last_clifo)
{
// Totale agente
fill_totage(curtab);
can_print = write_tab(tab);
// Scrive le righe che mancano
write_artcli_descrizioni(tab);
}
return can_print;
}
bool TStampa_schede::stampa_clifo(TCursor& cur, const TString& ragsoc, bool last_clifo)
{
const long items = cur.items();
TProgind* pi = NULL;
if (items > 4)
{
TString header(160);
header = TR("Preparazione file temporaneo di stampa ...");
if (ragsoc.not_empty())
header << '\n' << ragsoc;
pi = new TProgind(items, header, true, true);
}
cur.file().set_curr(new TDocumento);
TDocumento& doc = (TDocumento&)cur.file().curr();
TIsamtempfile* tab = new TIsamtempfile(LF_TAB, "svschede", true,true);
tab->setkey(2);
_form->relation()->replace(tab);
TRectype& curtab = tab->curr();
_totali.destroy();
_progressivo = 0;
bool can_print = true;
TForm_item& tit = _form->find_field('H',odd_page,FF_TITOLO);
tit.set(stampa_clienti() ? TR("clienti") : TR("fornitori"));
TForm_item& age = _form->find_field('H',odd_page,FF_AGENTE);
if (stampa_per_agente())
{
age.show();
age.set(_curagente);
}
else
age.hide();
for (cur = 0; cur.pos() < items && can_print; ++cur)
{
if (pi != NULL)
{
pi->addstatus(1);
if (pi->iscancelled())
{
can_print = false;
break;
}
}
if (stampa_sintetica())
{
if (fill_doc(curtab, doc))
{
can_print = write_tab(*tab);
if (can_print && stampa_per_agente())
update_totage(curtab);
}
}
else
{
_totriga.destroy();
for (int r = doc.physical_rows(); r > 0 && can_print; r--)
{
const TRiga_documento& rdoc = doc[r];
if (fill_rdoc(curtab, rdoc))
{
can_print = write_tab(*tab);
if (can_print)
{
if (stampa_per_documento())
update_totriga(curtab);
if (stampa_per_agente())
update_totage(curtab);
}
}
}
if (can_print && _totriga.items() > 0)
{
fill_totriga(curtab);
can_print = write_tab(*tab);
}
}
}
if (can_print && tab->items() > 0)
{
if (can_print && stampa_per_articolo())
can_print = write_totali_per_articolo(*tab);
if (can_print)
{
fill_tot(curtab);
can_print = write_tab(*tab);
}
if (can_print && stampa_per_agente() && last_clifo)
{
fill_totage(curtab);
can_print = write_tab(*tab);
}
}
if (pi != NULL)
delete pi;
if (can_print && tab->items() > 0)
{
TForm_item& col1 = _form->find_field('B',odd_page,FF_FIRSTCOLUMN);
TForm_item& col2 = _form->find_field('B',odd_page,FF_SECONDCOLUMN);
if (stampa_sintetica())
{
col1.set_col_head(TR("Base sconto"));
col2.set_col_head(TR("Totale"));
}
else
{
col1.set_col_head(TR("Netto scontato"));
col2.set_col_head(TR("Lordo scontato"));
}
_form->init_pictures(*_mask);
_form->print();
}
_form->relation()->replace(new TLocalisamfile(LF_TAB));
return can_print;
}
bool TStampa_schede::filtra_doc_per_stat(const TRelation* rel)
{
const TString16 tipodoc = rel->curr().get(DOC_TIPODOC);
const TRectype& tipo = cache().get("%TIP", tipodoc);
const bool stat = tipo.get_bool("B2");
return stat;
}
bool TStampa_schede::stampa_selezione(TCursor& clifocur, const TSheet& clifosheet,
const TString& filter)
{
const long clifos = clifosheet.items();
long toprint = clifosheet.checked();
if (toprint == 0) toprint = clifos;
const bool all = toprint == clifos;
const TRecnotype items = clifocur.items();
TString ragsoc;
TRelation rel(LF_DOC);
TRectype rec(LF_DOC);
bool cancel = false;
TProgind *pi = NULL;
// Inizializzazione solo per stampa agenti/articoli/clienti/documenti
if (stampa_per_ageart())
{
TForm_item& tit = _form->find_field('H',odd_page,FF_TITOLO);
tit.set(TR("agenti"));
TString header;
header = TR("Preparazione file temporaneo di stampa per l'agente: ");
header << _curagente;
pi = new TProgind(items, header, true, true);
// Sostituisce il file principale
TIsamtempfile* tab = new TIsamtempfile(LF_TAB, "svschede", true,true);
tab->setkey(2);
_form->relation()->replace(tab);
_progressivo = 0;
}
// printer().open(); // Spostata altrove
for (clifocur = 0; clifocur.pos() < clifos && toprint > 0 && !cancel; ++clifocur)
{
if (all || clifosheet.checked(clifocur.pos()))
{
const char tipocf = clifocur.curr().get_char(CLI_TIPOCF);
const long codcf = clifocur.curr().get_long(CLI_CODCF);
ragsoc = tipocf == 'C' ? TR("Cliente") : TR("Fornitore");
ragsoc << ' ' << codcf << " - " << clifocur.file().get(CLI_RAGSOC);
if (pi)
{
pi->addstatus(1L);
if (pi->iscancelled())
{
cancel = true;
break;
}
}
rec.put(DOC_TIPOCF, tipocf);
rec.put(DOC_CODCF, codcf);
rec.put(DOC_PROVV, _prov);
// Uso la chiave 2: TIPOCF+CODCF+PROVV+ANNO+DATADOC+CODNUM+NDOC
TCursor cur(&rel, filter, 2, &rec, &rec);
cur.set_filterfunction(filtra_doc_per_stat);
const TRecnotype tot = cur.items();
if (tot > 0)
{
cur.freeze();
if (stampa_per_ageart())
cancel = !raggruppa_articoli(cur, pi, toprint == 1);
else
cancel = !stampa_clifo(cur, ragsoc, toprint == 1);
cur.freeze(false);
}
toprint--;
}
}
// Stampa scheda agenti suddivisa per articoli/cliente/documento
if (!cancel && stampa_per_ageart())
{
pi->setstatus(items);
_form->init_pictures(*_mask);
if (_form->cursor()->items() > 0)
_form->print();
// Necessario fare il replace per la stampa del prossimo agente
// In modo che venga automaticamente cancellato il precedente file temporaneo
_form->relation()->replace(new TLocalisamfile(LF_TAB));
}
// printer().close(); Spostata altrove
if (pi)
delete pi;
return !cancel;
}
long TStampa_schede::clifo2index(TCursor_sheet& clifosheet, long codcf)
{
long i = -1;
const int codpos = _mask->get_int(SC_SORTCF); // Posizione del codice clifo nello sheet
if (codpos == 1)
{
long a = 0;
long b = clifosheet.items()-1;
while (a <= b)
{
i = (a+b)/2;
const long clifo = clifosheet.row(i).get_long(codpos);
if (clifo == codcf)
break;
if (clifo > codcf)
b = i-1;
else
a = i+1;
}
}
else
{
for (i = clifosheet.items()-1; i >= 0; i--)
{
TToken_string& row = clifosheet.row(i);
long clifo = row.get_long(codpos);
if (clifo == codcf)
break;
}
}
return i;
}
void TStampa_schede::main_loop()
{
TSchede_mask& m = *_mask;
while (m.run() != K_QUIT)
{
_clifo = m.get(SC_CLIFO)[0];
_tipo = m.get(F_TIPO)[0];
_sort = m.get(F_ORDINE)[0];
_prov = m.get(F_PROVVIS)[0];
_peragenti = m.get_bool(F_SORTAGENTI);
_perageart = m.get_bool(F_SORTAGEART);
_provvart = m.get_bool(F_PROVVART);
_fromdate = m.get_date(F_FROMDATE);
_todate = m.get_date(F_TODATE);
_fromnum = m.get(F_FROMNUM);
_tonum = m.get(F_TONUM);
_tipodoc = m.get(F_TIPODOC);
_form = new TSchede_form(_perageart ? "sv1100b" : "sv1100a");
_form->init(m.sfield(stampa_dettagliata() ? F_DETTAGLIATA : F_SINTETICA));
TString filter(80);
if (_fromdate.ok())
{
if (filter.not_empty()) filter << "&&";
filter << "(ANSI(" << DOC_DATADOC << ")>=\"" << _fromdate.string(ANSI) << "\")";
}
if (_todate.ok() && _todate >= _fromdate)
{
if (filter.not_empty()) filter << "&&";
filter << "(ANSI(" << DOC_DATADOC << ")<=\"" << _todate.string(ANSI) << "\")";
}
if (_fromnum.not_empty() && _fromnum == _tonum)
{
if (filter.not_empty()) filter << "&&";
filter << '(' << DOC_CODNUM << "==\"" << _fromnum << "\")";
}
else
{
if (_fromnum.not_empty())
{
if (filter.not_empty()) filter << "&&";
filter << '(' << DOC_CODNUM << ">=\"" << _fromnum << "\")";
}
if (_tonum.not_empty() && _tonum >= _fromnum)
{
if (filter.not_empty()) filter << "&&";
filter << '(' << DOC_CODNUM << "<=\"" << _tonum << "\")";
}
}
if (_tipodoc.not_empty())
{
if (filter.not_empty()) filter << "&&";
filter << '(' << DOC_TIPODOC << "==\"" << _tipodoc << "\")";
}
TCursor_sheet& clifosheet = m.cur_sheet();
TCursor& clifocur = *clifosheet.cursor();
const long clifos = clifocur.items();
long toprint = clifosheet.checked();
const bool all = toprint == 0 || toprint == clifos;
bool cancel = false;
printer().open(); // Spostata da stampa_selezione
if (stampa_per_agente())
{
TRelation relagenti(LF_AGENTI);
TRectype fromage(LF_AGENTI), toage(LF_AGENTI);
if (m.get(F_DAAGENTE).not_empty())
fromage.put(AGE_CODAGE, m.get(F_DAAGENTE));
if (m.get(F_ADAGENTE).not_empty())
toage.put(AGE_CODAGE, m.get(F_ADAGENTE));
TCursor curagenti(&relagenti, "", 1, &fromage, &toage);
const long ages = curagenti.items();
curagenti.freeze();
const TRectype& recagenti = curagenti.curr();
// Crea la lista degli agenti da stampare
TAssoc_array cia;
TRectype darec(LF_DOC), arec(LF_DOC);
int key = 0;
TString filterage = filter;
if (filterage.not_empty())
filterage << "&&";
filterage << '(' << DOC_CODAG << "!=\"\")";
if (!m.field(F_DAAGENTE).empty())
filterage << "&&(" << DOC_CODAG << ">=\"" << m.get(F_DAAGENTE) << "\")";
if (!m.field(F_ADAGENTE).empty())
filterage << "&&(" << DOC_CODAG << "<=\"" << m.get(F_ADAGENTE) << "\")";
if (_fromdate.ok() || _todate.ok())
{
key = 3;
filterage << "&&(" << DOC_TIPOCF << "=\"" << m.get_who() << "\")";
if (_fromdate.ok())
darec.put(DOC_DATADOC, _fromdate);
if (_todate.ok())
arec.put(DOC_DATADOC, _todate);
}
else
{
key = 2;
darec.put(DOC_TIPOCF, m.get_who());
arec.put(DOC_TIPOCF, m.get_who());
}
TRelation rel(LF_DOC);
TCursor cur(&rel, filterage, key, &darec, &arec);
cur.set_filterfunction(filtra_doc_per_stat);
const TRectype& curdoc = cur.curr();
const TRecnotype doc_items = cur.items();
if (doc_items > 0)
{
TProgind pi(doc_items, "Selezione documenti", true, true);
cur.freeze();
for (cur = 0L; cur.pos() < doc_items; ++cur)
{
pi.addstatus(1);
if (pi.iscancelled())
{
cancel = true;
break;
}
const TString& age = curdoc.get(DOC_CODAG);
CHECK(age.not_empty(), "Agente nullo");
TAssoc_array* sel = (TAssoc_array*)cia.objptr(age);
if (sel == NULL)
{
sel = new TAssoc_array;
cia.add(age, sel);
}
const TString& clifo = curdoc.get(DOC_CODCF);
sel->add(clifo, clifo);
}
}
for (curagenti = 0L; curagenti.pos() < ages && !cancel; ++curagenti)
{
_curagente = recagenti.get(AGE_CODAGE);
TAssoc_array* sel = (TAssoc_array*)cia.objptr(_curagente);
if (sel != NULL)
{
_totage.destroy(); // Azzera totali agente
clifosheet.uncheck(-1);
FOR_EACH_ASSOC_STRING((*sel), h, k, s)
{
const long i = clifo2index(clifosheet, atol(k));
if (i >= 0)
clifosheet.check(i);
}
filterage = filter;
if (filterage.not_empty())
filterage << "&&";
filterage << '(' << DOC_CODAG << "==\"" << _curagente << "\")";
_curagente << ' ' << recagenti.get(AGE_RAGSOC);
cancel = !stampa_selezione(clifocur, clifosheet, filterage);
}
}
}
else
{
_curagente.cut(0);
if (all)
{
TString msg;
msg.format(FR("Attenzione: e' stata selezionata la stampa di tutti i %s!\n"
"Si desidera continuare ugualmente?"),
m.get_who() == 'C' ? TR("clienti") : TR("fornitori"));
cancel = !yesno_box(msg);
}
if (!cancel)
stampa_selezione(clifocur, clifosheet, filter);
}
printer().close(); // Spostata da stampa_selezione
delete _form;
_form = NULL;
}
}
bool TStampa_schede::create()
{
open_files(LF_DOC, LF_RIGHEDOC, LF_CONDV, LF_RCONDV, LF_ANAMAG, LF_SCONTI, LF_UMART,
LF_TAB, LF_TABCOM, LF_CLIFO,LF_CFVEN, LF_INDSP, LF_OCCAS, LF_MOVMAG, LF_RMOVMAG,LF_PROVV, 0);
open_files(LF_SVRIEP,LF_SVSTAT,0);
_mask = new TSchede_mask;
return TSkeleton_application::create();
}
bool TStampa_schede::destroy()
{
delete _mask;
return true;
}
int sv1100(int argc, char* argv[])
{
TStampa_schede app;
app.run(argc, argv, TR("Stampa schede"));
return 0;
}