diff --git a/sv/f86.dir b/sv/f86.dir index d394d525a..6d986d86f 100755 --- a/sv/f86.dir +++ b/sv/f86.dir @@ -1,3 +1,3 @@ 86 0 -$svriep|0|0|95|0|Riepilogo statistiche di vendita||| +$svriep|2|15|98|0|Riepilogo statistiche di vendita||| diff --git a/sv/f86.trr b/sv/f86.trr index f94468110..9f3d90cc5 100755 --- a/sv/f86.trr +++ b/sv/f86.trr @@ -1,5 +1,5 @@ 86 -12 +13 ANNO|2|4|0|Anno solare PERIODO|2|3|0|Periodo di riferimento TIPODOC|1|4|0|Tipo documento @@ -8,9 +8,10 @@ CODART|1|20|0|Codice articolo UMQTA|1|2|0|Unita' di misura CODAG|1|5|0|Codice agente CODCF|1|6|0|Codice cliente/fornitore -LIVELLO|1|15|0|Livello di giacenza -CODMAG|1|5|0|Codice magazzino +ZONA|1|3|0|Codice Zona +GIAC|1|15|0|Livello di giacenza +MAG|1|5|0|Codice magazzino QUANTITA|4|11|3|Quantita VALORE|4|18|2|Valore 1 -ANNO+PERIODO+TIPODOC+TIPOART+CODART+UMQTA+CODAG+CODCF+LIVELLO+CODMAG| +ANNO+PERIODO+TIPODOC+TIPOART+CODART+UMQTA+CODAG+CODCF+ZONA+GIAC| diff --git a/sv/sv0.cpp b/sv/sv0.cpp index 45bef6d0b..ad2605638 100755 --- a/sv/sv0.cpp +++ b/sv/sv0.cpp @@ -8,8 +8,11 @@ int main(int argc, char** argv) int n = argc > 1 ? atoi(argv[1]+1) : 0; switch(n) { + case 0: + sv0100(argc, argv); + break; case 3: - st0400(argc, argv); + sv0400(argc, argv); break; default: error_box("Invalid argument %s", argv[1]); diff --git a/sv/sv0.h b/sv/sv0.h index 5873f150c..dfce9dd5d 100755 --- a/sv/sv0.h +++ b/sv/sv0.h @@ -1,9 +1,9 @@ -#ifndef __ST0_H -#define __ST0_H +#ifndef __SV0_H +#define __SV0_H -int st0100(int argc, char* argv[]); -int st0200(int argc, char* argv[]); -int st0300(int argc, char* argv[]); -int st0400(int argc, char* argv[]); +int sv0100(int argc, char* argv[]); +int sv0200(int argc, char* argv[]); +int sv0300(int argc, char* argv[]); +int sv0400(int argc, char* argv[]); #endif diff --git a/sv/sv0400.cpp b/sv/sv0400.cpp index 4443582ed..e76bce980 100755 --- a/sv/sv0400.cpp +++ b/sv/sv0400.cpp @@ -8,7 +8,7 @@ class TParametri_stat : public TConfig_application bool _ask_update; protected: - virtual bool postprocess_config_changed (const char* par, const char* var, const char* oldv, const char* newv); + virtual bool postprocess_config_changed (const char*, const char*, const char*, const char*); virtual bool user_destroy(); public: @@ -39,7 +39,7 @@ TParametri_stat::TParametri_stat() : TConfig_application(CONFIG_DITTA), _ask_update(FALSE) { } -int st0400(int argc, char* argv[]) +int sv0400(int argc, char* argv[]) { TParametri_stat app; app.run(argc, argv, "Parametri statistiche"); diff --git a/sv/sv0400a.h b/sv/sv0400a.h index 8abf8666a..8374aadaf 100755 --- a/sv/sv0400a.h +++ b/sv/sv0400a.h @@ -11,7 +11,8 @@ #define F_RAGGRUPPA_OMAGGI 114 #define F_AGENTE 121 #define F_CLIENTE 122 -#define F_GIACENZA 123 -#define F_MAGAZZINO 124 +#define F_ZONA 123 +#define F_GIACENZA 124 +#define F_MAGAZZINO 125 #endif diff --git a/sv/sv0400a.uml b/sv/sv0400a.uml index 140ffaff3..3baa6d99a 100755 --- a/sv/sv0400a.uml +++ b/sv/sv0400a.uml @@ -21,15 +21,18 @@ BEGIN PROMPT 1 1 "@bFrequenza di raggruppamento" END -LIST F_FREQUENZA 1 20 +LIST F_FREQUENZA 1 15 BEGIN PROMPT 2 2 "Frequenza " ITEM "G|Giornaliera" ITEM "S|Settimanale" ITEM "Q|Quindicinale" - ITEM "M|Mensile" - ITEM "B|Bimestrale" - ITEM "T|Trimestrale" + ITEM "1|Mensile" + ITEM "2|Bimestrale" + ITEM "3|Trimestrale" + ITEM "4|Quadrimestrale" + ITEM "6|Semestrale" + ITEM "A|Annuale" FIELD Frequenza END @@ -130,15 +133,21 @@ BEGIN FIELD ClienteGrp END +BOOLEAN F_ZONA +BEGIN + PROMPT 40 17 "Zona" + FIELD ZonaGrp +END + BOOLEAN F_GIACENZA BEGIN - PROMPT 40 17 "Giacenza" + PROMPT 40 18 "Giacenza" FIELD GiacenzaGrp END BOOLEAN F_MAGAZZINO BEGIN - PROMPT 40 18 "Magazzino" + PROMPT 40 19 "Magazzino" FIELD MagazzinoGrp END diff --git a/sv/sv1.cpp b/sv/sv1.cpp index 5633d32a3..251435362 100755 --- a/sv/sv1.cpp +++ b/sv/sv1.cpp @@ -8,12 +8,9 @@ int main(int argc, char** argv) int n = argc > 1 ? atoi(argv[1]+1) : 0; switch(n) { - case 0: - sv1100(argc, argv); - break; - default: - error_box("Invalid argument %s", argv[1]); - break; + case 0 : sv1100(argc, argv); break; + case 1 : sv1200(argc, argv); break; + default: error_box("Invalid argument %s", argv[1]); break; } exit(0); return 0; diff --git a/sv/sv1.h b/sv/sv1.h index d73f3ab26..235c4a974 100755 --- a/sv/sv1.h +++ b/sv/sv1.h @@ -2,5 +2,6 @@ #define __SV1_H int sv1100(int argc, char* argv[]); +int sv1200(int argc, char* argv[]); #endif diff --git a/sv/sv1100a.uml b/sv/sv1100a.uml index 8e6194f15..17cb92f0a 100755 --- a/sv/sv1100a.uml +++ b/sv/sv1100a.uml @@ -127,14 +127,14 @@ END RADIOBUTTON F_PROVVIS 1 24 BEGIN - PROMPT 1 15 "Tipo movimenti" + PROMPT 1 15 "@bTipo movimenti" ITEM "D|Definitivi" ITEM "P|Provvisori" END RADIOBUTTON F_TIPO 1 26 BEGIN - PROMPT 27 15 "Tipo stampa" + PROMPT 27 15 "@bTipo stampa" ITEM "S|Sintetica" MESSAGE CLEAR,F_ORDINE ITEM "D|Dettagliata" @@ -143,7 +143,7 @@ END RADIOBUTTON F_ORDINE 1 24 BEGIN - PROMPT 55 15 "Ordinamento" + PROMPT 55 15 "@bOrdinamento" ITEM "D|Documento" ITEM "A|Articolo" END @@ -161,7 +161,7 @@ SPREADSHEET F_SINTETICA 0 8 BEGIN PROMPT 1 2 "" ITEM "Campo@12" - ITEM "Testata@12" + ITEM "Intestazione@17" ITEM "Descrizione@50" ITEM "Importo" END @@ -175,7 +175,7 @@ SPREADSHEET F_DETTAGLIATA BEGIN PROMPT 1 12 "" ITEM "Campo@12" - ITEM "Testata@12" + ITEM "Intestazione@17" ITEM "Descrizione@50" ITEM "Importo" END @@ -199,7 +199,7 @@ BEGIN CHECKTYPE NORMAL END -STRING S_HEAD 15 +STRING S_HEAD 17 BEGIN PROMPT 1 2 "Intestazione " END @@ -212,7 +212,7 @@ END BOOLEAN S_IMPORTO BEGIN - PROMPT 1 4 "Importo" + PROMPT 41 1 "Importo" FLAGS "D" END @@ -250,7 +250,7 @@ BEGIN CHECKTYPE NORMAL END -STRING S_HEAD 15 +STRING S_HEAD 17 BEGIN PROMPT 1 2 "Intestazione " END @@ -263,7 +263,7 @@ END BOOLEAN S_IMPORTO BEGIN - PROMPT 1 4 "Importo" + PROMPT 41 1 "Importo" FLAGS "D" END diff --git a/sv/svlib01.cpp b/sv/svlib01.cpp index fc9deefbb..df953f42c 100755 --- a/sv/svlib01.cpp +++ b/sv/svlib01.cpp @@ -6,58 +6,117 @@ #include "svriep.h" /////////////////////////////////////////////////////////// -// TStats_agg +// Funzioni di utilita' comune /////////////////////////////////////////////////////////// -void TStats_agg::init() -{ - TConfig ini(CONFIG_DITTA, "sv"); +TFrequenza_statistiche char2frequency(char c) +{ + const TFixed_string list(" GSQ12346A"); + TFrequenza_statistiche f = TFrequenza_statistiche(list.find(c)); + return f; +} - switch(ini.get_char("Frequenza")) +char frequency2char(TFrequenza_statistiche f) +{ + const char* list = " GSQ12346A"; + return list[f]; +} + +int last_period(int anno, TFrequenza_statistiche f) +{ + int n = 0; + switch(f) { - case 'B': _frequenza = fs_bimestrale; break; - case 'M': _frequenza = fs_mensile; break; - case 'Q': _frequenza = fs_quindicinale; break; - case 'S': _frequenza = fs_settimanale; break; - case 'T': _frequenza = fs_trimestrale; break; - default : _frequenza = fs_giornaliera; break; + case fs_giornaliera : n = 365 + (TDate::last_day(2, anno) == 29); break; + case fs_settimanale : n = 52; break; + case fs_quindicinale : n = 24; break; + case fs_mensile : n = 12; break; + case fs_bimestrale : n = 6; break; + case fs_trimestrale : n = 4; break; + case fs_quadrimestrale : n = 3; break; + case fs_semestrale : n = 2; break; + case fs_annuale : n = 1; break; + default: NFCHECK("Invalid frequency"); } - - _merce = ini.get_bool("StatMerce"); - _prestazioni = ini.get_bool("StatPrestazioni"); - _omaggi = ini.get_bool("StatOmaggi"); - _omaggio_is_merce = ini.get_bool("OmaggioIsMerce"); - - _art_nocode = ini.get_bool("ArtNoCode"); - _art_noanag = ini.get_bool("ArtNoAnag"); - _art_noanag_grp = ini.get_bool("ArtNoAnagGrp"); - - _agente = ini.get_bool("AgenteGrp"); - _cliente = ini.get_bool("ClienteGrp"); - _giacenza = ini.get_bool("GiacenzaGrp"); - _magazzino = ini.get_bool("MagazzinoGrp"); + return n; } -void TStats_agg::test_firm() const +int divide(TFrequenza_statistiche f1, TFrequenza_statistiche f2) { - const long ditta = prefix().get_codditta(); - if (ditta != _ditta) - { - CHECK(_data.items() == 0, "Non cambiare ditta durante un'operazione di ricalcolo!"); - ((TStats_agg*)this)->init(); - ((TStats_agg*)this)->_ditta = ditta; + CHECK(f1 >= f2 && f2 != fs_nulla, "Invalid frequency division"); + + if (f1 == f2) + return 1; + + switch (f1) + { + case fs_annuale: + switch(f2) + { + case fs_semestrale : return 2; + case fs_quadrimestrale: return 3; + case fs_trimestrale : return 4; + case fs_bimestrale : return 6; + case fs_mensile : return 12; + case fs_quindicinale : return 24; + case fs_settimanale : return 52; + default : break; + } + break; + case fs_semestrale: + switch(f2) + { + case fs_trimestrale :return 2; + case fs_bimestrale :return 3; + case fs_mensile :return 6; + case fs_quindicinale :return 12; + case fs_settimanale :return 26; + default :break; + } + break; + case fs_quadrimestrale: + switch(f2) + { + case fs_bimestrale :return 2; + case fs_mensile :return 4; + case fs_quindicinale :return 8; + default :break; + } + case fs_trimestrale: + switch(f2) + { + case fs_mensile :return 3; + case fs_quindicinale :return 6; + case fs_settimanale :return 13; + default :break; + } + break; + case fs_bimestrale: + switch(f2) + { + case fs_mensile :return 2; + case fs_quindicinale :return 4; + default :break; + } + break; + case fs_mensile: + if (f2 == fs_quindicinale) + return 2; + break; + default: + break; } + + return 0; } -int TStats_agg::date2period(const TDate& datadoc) const +int date2period(const TDate& datadoc, TFrequenza_statistiche freq) { - test_firm(); - int classe; - if (_frequenza > fs_settimanale) + if (freq > fs_settimanale) { classe = datadoc.month(); - switch(_frequenza) + switch(freq) { case fs_quindicinale: classe = (classe-1) * 2 + 1; @@ -69,7 +128,16 @@ int TStats_agg::date2period(const TDate& datadoc) const case fs_trimestrale: classe = (classe-1) / 3 + 1; break; - default: + case fs_quadrimestrale: + classe = (classe-1) / 4 + 1; + break; + case fs_semestrale: + classe = (classe-1) / 6 + 1; + break; + case fs_annuale: + classe = 1; + break; + default: // fs_mensile break; } } @@ -77,18 +145,147 @@ int TStats_agg::date2period(const TDate& datadoc) const { const TDate primo(1, 1, datadoc.year()); classe = int(datadoc - primo); - if (_frequenza == fs_settimanale) + if (freq == fs_settimanale) + { classe /= 7; + if (classe > 51) classe = 51; + } classe++; } return classe; } +const TDate& floor(TDate& data, TFrequenza_statistiche freq) +{ + switch (freq) + { + case fs_settimanale: + { + const TDate primo(1, 1, data.year()); + int settimana = int((data - primo) / 7); + if (settimana > 51) settimana = 51; + data = primo; + data += settimana * 7; + } + break; + case fs_quindicinale: + data.set_day(data.day() <= 15 ? 1 : 16); + break; + case fs_mensile: + data.set_day(1); + break; + case fs_bimestrale: + data.set_day(1); + data.set_month(((data.month()-1) / 2) * 2 + 1); + break; + case fs_trimestrale: + data.set_day(1); + data.set_month(((data.month()-1) / 3) * 3 + 1); + break; + case fs_quadrimestrale: + data.set_day(1); + data.set_month(((data.month()-1) / 4) * 4 + 1); + break; + case fs_semestrale: + data.set_day(1); + data.set_month(data.month() <= 6 ? 1 : 7); + break; + case fs_annuale: + data.set_day(1); + data.set_month(1); + break; + default: break; + } + return data; +} + +const TDate& ceil(TDate& data, TFrequenza_statistiche freq) +{ + floor(data, freq); + switch (freq) + { + case fs_settimanale: + data += 6; + if (data.month() == 12 && data.day() >= 29) + data.set_end_month(); + break; + case fs_quindicinale: + if (data.day() == 1) + data.set_day(15); + else + data.set_end_month(); + break; + case fs_mensile: + data.set_end_month(); + break; + case fs_bimestrale: + data.addmonth(1); + data.set_end_month(); + break; + case fs_trimestrale: + data.addmonth(2); + data.set_end_month(); + break; + case fs_quadrimestrale: + data.addmonth(3); + data.set_end_month(); + break; + case fs_semestrale: + data.addmonth(5); + data.set_end_month(); + break; + case fs_annuale: + data.set_month(12); + data.set_day(31); + break; + default: break; + } + return data; +} + +/////////////////////////////////////////////////////////// +// TStats_agg +/////////////////////////////////////////////////////////// + +void TStats_agg::init() +{ + _ditta = prefix().get_codditta(); + + TConfig ini(CONFIG_DITTA, "sv"); + + _frequenza = char2frequency(ini.get_char("Frequenza")); + _merce = ini.get_bool("StatMerce"); + _prestazioni = ini.get_bool("StatPrestazioni"); + _omaggi = ini.get_bool("StatOmaggi"); + _omaggio_is_merce = ini.get_bool("OmaggioIsMerce"); + + _art_nocode = ini.get_bool("ArtNoCode"); + _art_noanag = ini.get_bool("ArtNoAnag"); + _art_noanag_grp = ini.get_bool("ArtNoAnagGrp"); + + _agente = ini.get_bool("AgenteGrp"); + _cliente = ini.get_bool("ClienteGrp"); + _zona = ini.get_bool("ZonaGrp"); + _giacenza = ini.get_bool("GiacenzaGrp"); + _magazzino = ini.get_bool("MagazzinoGrp"); +} + +void TStats_agg::test_firm() const +{ + const long ditta = prefix().get_codditta(); + if (ditta > 0 && ditta != _ditta) + { + CHECK(_data.items() == 0, "Non cambiare ditta durante un'operazione di ricalcolo!"); + ((TStats_agg*)this)->init(); + } +} + void TStats_agg::put_key(TRectype& stat, TToken_string& key) const { CHECK(stat.num() == LF_SVRIEP, "Ci vuole un record delle statistiche"); stat.zero(); - stat.put(SVR_ANNO, key.get(0)); + key.restart(); + stat.put(SVR_ANNO, key.get()); stat.put(SVR_PERIODO, key.get()); stat.put(SVR_TIPODOC, key.get()); stat.put(SVR_TIPOART, key.get()); @@ -96,8 +293,9 @@ void TStats_agg::put_key(TRectype& stat, TToken_string& key) const stat.put(SVR_UMQTA, key.get()); stat.put(SVR_CODAG, key.get()); stat.put(SVR_CODCF, key.get()); - stat.put(SVR_LIVELLO, key.get()); - stat.put(SVR_CODMAG, key.get()); + stat.put(SVR_ZONA, key.get()); + stat.put(SVR_GIAC, key.get()); + stat.put(SVR_MAG, key.get()); } TStats_agg::TStats_data& TStats_agg::find(const TRiga_documento& rdoc) @@ -140,6 +338,11 @@ TStats_agg::TStats_data& TStats_agg::find(const TRiga_documento& rdoc) else key.add(""); + if (_zona) + key.add(doc.get(DOC_ZONA)); + else + key.add(""); + if (_giacenza) key.add(rdoc.get(RDOC_LIVELLO)); else @@ -282,6 +485,6 @@ bool TStats_agg::update() return ok; } -TStats_agg::TStats_agg() : _ditta(0) +TStats_agg::TStats_agg() : _ditta(-1) { } diff --git a/sv/svlib01.h b/sv/svlib01.h index e98a349f7..9ab9df3e0 100755 --- a/sv/svlib01.h +++ b/sv/svlib01.h @@ -9,12 +9,32 @@ #include "..\ve\velib.h" #endif +enum TFrequenza_statistiche { fs_nulla, fs_giornaliera, + fs_settimanale, fs_quindicinale, + fs_mensile, fs_bimestrale, + fs_trimestrale, fs_quadrimestrale, + fs_semestrale, fs_annuale }; +// Converte una carattere in una frequenza delle statisitiche +TFrequenza_statistiche char2frequency(char c); +// Converte una frequenza delle statisitiche in un carattere +char frequency2char(TFrequenza_statistiche f); + +// Arrotondamento di una data alla frequenza specificata +const TDate& floor(TDate& data, TFrequenza_statistiche freq); +const TDate& ceil(TDate& data, TFrequenza_statistiche freq); + +// Ritorna il rapporto tra le frequenze: 0 se impossibile stabilirlo +int divide(TFrequenza_statistiche f1, TFrequenza_statistiche f2); + +// Ritorna l'ultimo perido di un anno (primo = 1) +int last_period(int anno, TFrequenza_statistiche freq); + +// Converte una data nella classe temporale definita dalla frequenza +int date2period(const TDate& data, TFrequenza_statistiche freq); + class TStats_agg : public TObject { - enum TFrequenza_statistiche { fs_giornaliera, fs_settimanale, fs_quindicinale, - fs_mensile, fs_bimestrale, fs_trimestrale }; - class TStats_data : public TObject { public: @@ -27,7 +47,7 @@ class TStats_agg : public TObject TFrequenza_statistiche _frequenza; bool _merce, _prestazioni, _omaggi, _omaggio_is_merce; bool _art_nocode, _art_noanag, _art_noanag_grp; - bool _agente, _cliente, _articolo, _giacenza, _magazzino; + bool _agente, _cliente, _zona, _articolo, _giacenza, _magazzino; protected: void test_firm() const; @@ -35,16 +55,27 @@ protected: TStats_agg::TStats_data& find(const TRiga_documento& rdoc); bool can_add(const TRiga_documento& rdoc) const; - public: void init(); void reset(); bool sub(const TRiga_documento& rdoc); bool add(const TRiga_documento& rdoc); bool update(); - - // Converte una data nella classe temporale definita dalla frequenza delle statisitiche - int date2period(const TDate& datadoc) const; + + TFrequenza_statistiche frequency() const + { return _frequenza; } + + int date2period(const TDate& datadoc) const + { return ::date2period(datadoc, _frequenza); } + + bool grp_agente() const { test_firm(); return _agente; } + bool grp_cliente() const { test_firm(); return _cliente; } + bool grp_zona() const { test_firm(); return _zona; } + bool grp_articolo() const { test_firm(); return _articolo; } + bool grp_giacenza() const { test_firm(); return _giacenza; } + bool grp_magazzino() const { test_firm(); return _magazzino; } + + bool omaggio_is_merce() const { test_firm(); return _omaggio_is_merce; } TStats_agg(); virtual ~TStats_agg() { } diff --git a/sv/svriep.h b/sv/svriep.h index b74a50e28..706ae15bf 100755 --- a/sv/svriep.h +++ b/sv/svriep.h @@ -9,8 +9,9 @@ #define SVR_UMQTA "UMQTA" #define SVR_CODAG "CODAG" #define SVR_CODCF "CODCF" -#define SVR_LIVELLO "LIVELLO" -#define SVR_CODMAG "CODMAG" +#define SVR_ZONA "ZONA" +#define SVR_GIAC "GIAC" +#define SVR_MAG "MAG" #define SVR_QUANTITA "QUANTITA" #define SVR_VALORE "VALORE"