Patch level : 10.0 nopatch
Files correlati : pd6342.exe Ricompilazione Demo : [ ] Commento Habilita ripartizione ricorsiva step 1 git-svn-id: svn://10.65.10.50/branches/R_10_00@20855 c028cbd2-c16b-5b4b-a496-9718f37d4682
This commit is contained in:
parent
96349866da
commit
b72f5caffb
@ -37,6 +37,8 @@ Esportazione clienti e indirizzi di spedizione Pharmatex (solo msk e rep)
|
||||
|
||||
PD6342
|
||||
Stampa dei costi/ricavi analitici per anno riproporzionati per mese (Habilita)
|
||||
Importazione di movimenti in Analitica (Habilita)
|
||||
Ribaltamento ricorsivo movimenti di Analitica (Habilita)
|
||||
|
||||
|
||||
- PG -------------------------------------------------------------------------------------------------------------
|
||||
|
@ -9,6 +9,7 @@ int main(int argc, char** argv)
|
||||
{
|
||||
case 0: pd6342100(argc, argv); break; //stampa costi/ricavi mensili per Habilita
|
||||
case 1: pd6342200(argc, argv); break; //importatore di movimenti in analitica per Habilita
|
||||
case 2: pd6342300(argc, argv); break; //ribaltamento ricorsivo movimenti per Habilita
|
||||
default: pd6342100(argc, argv); break; //stampa costi/ricavi mensili per Habilita
|
||||
}
|
||||
return 0;
|
||||
|
@ -1,2 +1,3 @@
|
||||
int pd6342100(int argc, char* argv[]);
|
||||
int pd6342200(int argc, char* argv[]);
|
||||
int pd6342200(int argc, char* argv[]);
|
||||
int pd6342300(int argc, char* argv[]);
|
347
ps/pd6342300.cpp
Executable file
347
ps/pd6342300.cpp
Executable file
@ -0,0 +1,347 @@
|
||||
#include <applicat.h>
|
||||
#include <automask.h>
|
||||
#include <defmask.h>
|
||||
#include <recarray.h>
|
||||
#include <relation.h>
|
||||
|
||||
#include "../cg/cglib01.h"
|
||||
#include "../ca/calib01.h"
|
||||
#include "../ca/calib02.h"
|
||||
|
||||
#include "pd6342.h"
|
||||
#include "pd6342300a.h"
|
||||
|
||||
#include "../ca/movana.h"
|
||||
#include "../ca/rmovana.h"
|
||||
#include "../ca/rip.h"
|
||||
#include "../ca/rrip.h"
|
||||
|
||||
//--------------------------------------------------------------------
|
||||
// MASCHERA
|
||||
//--------------------------------------------------------------------
|
||||
class TRib_movanal_msk : public TAnal_report_mask
|
||||
{
|
||||
protected:
|
||||
virtual bool on_field_event(TOperable_field& o, TField_event e, long jolly);
|
||||
|
||||
public:
|
||||
TRib_movanal_msk();
|
||||
};
|
||||
|
||||
|
||||
bool TRib_movanal_msk::on_field_event(TOperable_field& o, TField_event e, long jolly)
|
||||
{
|
||||
switch (o.dlg())
|
||||
{
|
||||
case F_DATAINI:
|
||||
case F_DATAFIN:
|
||||
if (e == fe_close)
|
||||
{
|
||||
const int anno = get_int(F_ANNO);
|
||||
|
||||
TEsercizi_contabili esc; //..le date devono essere incluse nell'esercizio selezionato!
|
||||
const TDate data(o.get());
|
||||
if (!data.empty() && esc.date2esc(data) != anno)
|
||||
return error_box(TR("La data deve appartenere all'anno selezionato"));
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return TAnal_report_mask::on_field_event(o, e, jolly);
|
||||
}
|
||||
|
||||
TRib_movanal_msk::TRib_movanal_msk() : TAnal_report_mask("ca2200a")
|
||||
{
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------
|
||||
// APPLICAZIONE
|
||||
//--------------------------------------------------------------------
|
||||
class TRib_movanal_app : public TSkeleton_application
|
||||
{
|
||||
TCache_ripartizioni _cache_rip;
|
||||
bool _definitivo;
|
||||
|
||||
protected:
|
||||
virtual void main_loop();
|
||||
|
||||
bool elabora_righe(TAnal_mov& anal_mov, TRecord_array& input_rows, TRecord_array& output_rows);
|
||||
bool ripartizione(const TAnal_ripartizioni_batch& rrip, const TRectype& rec, TRecord_array& output_rows);
|
||||
bool pareggio(TAnal_mov& anal_mov, const TAnal_ripartizioni_batch& rrip, const TRectype& rec, TRecord_array& output_rows);
|
||||
|
||||
public:
|
||||
bool elabora_movimento(TAnal_mov& anal_mov, const bool esplodi);
|
||||
TRib_movanal_app(){}
|
||||
};
|
||||
|
||||
|
||||
bool TRib_movanal_app::pareggio(TAnal_mov& anal_mov, const TAnal_ripartizioni_batch& rrip, const TRectype& rec,
|
||||
TRecord_array& output_rows)
|
||||
{
|
||||
bool ho_pareggiato = false;
|
||||
|
||||
TImporto totdoc(anal_mov.get_char(MOVANA_SEZIONE), anal_mov.get_real(MOVANA_TOTDOC));
|
||||
|
||||
const TImporto imp_riga(rec.get_char(RMOVANA_SEZIONE), rec.get_real(RMOVANA_IMPORTO));
|
||||
|
||||
totdoc -= imp_riga;
|
||||
totdoc.normalize();
|
||||
anal_mov.put(MOVANA_TOTDOC, totdoc.valore());
|
||||
anal_mov.put(MOVANA_SEZIONE, totdoc.sezione());
|
||||
|
||||
//aggiunge la riga originale alle righe di output (e' un pareggio)
|
||||
const int original_nriga = output_rows.rows() + 1;
|
||||
TRectype* newrec = new TRectype(rec);
|
||||
newrec->put(RMOVANA_NUMRIG, original_nriga);
|
||||
output_rows.add_row(newrec);
|
||||
|
||||
//swappa la sezione e la manda al ripartitore in modo da generare righe con la sezione rovesciata rispetto a quella..
|
||||
//..originale ed ottenere cosi' il pareggio
|
||||
TRectype swaprec(rec);
|
||||
swaprec.put(RMOVANA_SEZIONE, imp_riga.sezione() == 'D' ? 'A' : 'D');
|
||||
ho_pareggiato = ripartizione(rrip, swaprec, output_rows);
|
||||
|
||||
//elimina il codcontoori da tutte le righe aggiunte per il pareggio
|
||||
for (int i = output_rows.rows(); i > original_nriga; i--)
|
||||
output_rows.row(i, false).zero(RMOVANA_CODCONTORI);
|
||||
|
||||
return ho_pareggiato;
|
||||
}
|
||||
|
||||
|
||||
bool TRib_movanal_app::ripartizione(const TAnal_ripartizioni_batch& rrip, const TRectype& rec, TRecord_array& output_rows)
|
||||
{
|
||||
bool ho_ripartito = false;
|
||||
// Importo totale da distribuire arrotondato ai decimali della valuta di conto
|
||||
TGeneric_distrib distrib(rec.get_real(RMOVANA_IMPORTO), TCurrency::get_firm_dec());
|
||||
|
||||
// Calcolo tutte le percentuali da ripartire
|
||||
int i;
|
||||
const int righe_ripartizione = rrip.rows();
|
||||
for (i = 1; i <= rrip.rows(); i++)
|
||||
{
|
||||
const real importanza_riga = rrip[i].get_real(RRIP_RIPARTO);
|
||||
distrib.add(importanza_riga);
|
||||
}
|
||||
|
||||
for (i = 1; i <= righe_ripartizione; i++)
|
||||
{
|
||||
const real imp = distrib.get(); // Legge la quota da distribuire
|
||||
|
||||
if (imp != ZERO)
|
||||
{
|
||||
TRectype* newrec = new TRectype(rec);
|
||||
newrec->put(RMOVANA_NUMRIG, output_rows.rows() + 1);
|
||||
newrec->put(RMOVANA_IMPORTO, imp); //e la mette nella nuova riga
|
||||
//poi copia i valori dei campi cdc,cms,fsc,in quelli di tipo ori (nello stesso record)
|
||||
ca_copia_campo(rec, RMOVANA_CODCCOSTO, *newrec, RMOVANA_CODCCORI);
|
||||
ca_copia_campo(rec, RMOVANA_CODCMS, *newrec, RMOVANA_CODCMSORI);
|
||||
ca_copia_campo(rec, RMOVANA_CODFASE, *newrec, RMOVANA_CODFASEORI);
|
||||
ca_copia_campo(rec, RMOVANA_CODCONTO, *newrec, RMOVANA_CODCONTORI);
|
||||
//e mette nei campi std i valori che trova nelle righe ripartizione
|
||||
ca_copia_campo(rrip[i], RRIP_CODCOSTO, *newrec, RMOVANA_CODCCOSTO);
|
||||
ca_copia_campo(rrip[i], RRIP_CODCMS, *newrec, RMOVANA_CODCMS);
|
||||
ca_copia_campo(rrip[i], RRIP_CODFASE, *newrec, RMOVANA_CODFASE);
|
||||
ca_copia_campo(rrip[i], RRIP_CODCONTO, *newrec, RMOVANA_CODCONTO);
|
||||
|
||||
output_rows.add_row(newrec);
|
||||
ho_ripartito = true;
|
||||
} //if(imp!=ZERO)...
|
||||
} //for(i=1;i<=righe_ripartizione...
|
||||
|
||||
return ho_ripartito;
|
||||
}
|
||||
|
||||
|
||||
bool TRib_movanal_app::elabora_righe(TAnal_mov& anal_mov, TRecord_array& input_rows, TRecord_array& output_rows)
|
||||
{
|
||||
bool ho_cambiato_qualchecosa = false;
|
||||
|
||||
const int annoes = anal_mov.get_int(MOVANA_ANNOES);
|
||||
const char tipomov = anal_mov.get_char(MOVANA_TIPOMOV);
|
||||
int loop = 0;
|
||||
|
||||
while (loop < 50)
|
||||
{
|
||||
bool modified = false;
|
||||
for (int r = 1; r <= input_rows.rows(); r++)
|
||||
{
|
||||
const TRectype& rec = input_rows.row(r);
|
||||
TAnal_bill zio(rec);
|
||||
const int rmovana_indbil = zio.indicatore_bilancio();
|
||||
|
||||
//ripartizione batch: passa il conto perche' per prima cosa provera' una ripartizione di tipo 'P' con chiave 3; se non..
|
||||
//..ci riuscira', provera' da solo (metodi della TCache_ripartizioni) le ripartizioni di tipo 'B' con chiave 4.
|
||||
const TAnal_ripartizioni_batch& rrip = _cache_rip.righe(zio, annoes, rmovana_indbil, tipomov);
|
||||
const char tiporip = rrip.tiporip();
|
||||
|
||||
//ci sono righe di ripartizione
|
||||
const int righe_ripartizione = rrip.rows();
|
||||
bool ripartisci = righe_ripartizione > 0;
|
||||
|
||||
//se ci sono righe di ripartizione/pareggio si va a ripartire!
|
||||
if (ripartisci)
|
||||
{
|
||||
switch (tiporip)
|
||||
{
|
||||
//procedura di ripartizione batch 'B' originale; se tiporip=='P' invece ci vuole il pareggio del movana
|
||||
case 'B':
|
||||
modified |= ripartizione(rrip, rec, output_rows);
|
||||
break;
|
||||
case 'P':
|
||||
modified |= pareggio(anal_mov, rrip, rec, output_rows);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
else //if(ripartisci... nessuna riga di ripartizione->aggiungo la riga input all'output
|
||||
{
|
||||
TRectype* newrec = new TRectype(rec);
|
||||
newrec->put(RMOVANA_NUMRIG, output_rows.rows() + 1);
|
||||
output_rows.add_row(newrec);
|
||||
}
|
||||
} //for(int r=1; r<=input_rows.rows()...
|
||||
if (modified)
|
||||
{
|
||||
ho_cambiato_qualchecosa = true;
|
||||
input_rows = output_rows;
|
||||
}
|
||||
else
|
||||
break;
|
||||
}
|
||||
return ho_cambiato_qualchecosa;
|
||||
}
|
||||
|
||||
|
||||
bool TRib_movanal_app::elabora_movimento(TAnal_mov& anal_mov, const bool esplodi)
|
||||
{
|
||||
TRecord_array& input_rows = anal_mov.body(); //record_array con le righe del mov_anal (INPUT)
|
||||
bool do_rewrite = false;
|
||||
|
||||
//Per prima cosa prende le righe del movimento su RMOVANA e le ricompatta..
|
||||
TRecord_array compact_rows = input_rows; //record array con le righe compattate da creare con la..
|
||||
compact_rows.destroy_rows(); //..implode_rows(); intanto le azzera per sicurezza
|
||||
|
||||
if (esplodi)
|
||||
{
|
||||
//Imploditore
|
||||
ca_implode_rows(input_rows, compact_rows);
|
||||
//..poi lo riesplode in tutte le righe che possono nascere secondo le regole delle ripartizioni!
|
||||
TRecord_array output_rows = input_rows; //crea il record_array di output come copia dell'INPUT..
|
||||
output_rows.destroy_rows(); //..e poi lo pulisce
|
||||
|
||||
//Esploditore
|
||||
if (elabora_righe(anal_mov, compact_rows, output_rows))
|
||||
{
|
||||
input_rows = output_rows; //rimette i record elaborati negli originali
|
||||
do_rewrite = true;
|
||||
}
|
||||
|
||||
if (_definitivo) //se l'elaborazione e' definitiva...
|
||||
{
|
||||
anal_mov.put(MOVANA_BLOCCATO, 'X'); //..mette bloccato = X nella testata del movimento
|
||||
do_rewrite = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//Imploditore
|
||||
do_rewrite = ca_implode_rows(input_rows, compact_rows);
|
||||
if (do_rewrite)
|
||||
{
|
||||
input_rows = compact_rows; // rimette i record compattati negli originali
|
||||
anal_mov.update_totdoc(); //aggiorna il totale movana (necessarip per ripartizioni a pareggio, di sicurezza per le altre)
|
||||
}
|
||||
}
|
||||
|
||||
return do_rewrite; //se ha elaborato delle righe e/o e' una elaborazione definitiva, riscrive la..
|
||||
}
|
||||
|
||||
static bool ripartisci_callback(const TRelation& rel, void* pJolly)
|
||||
{
|
||||
TRib_movanal_app& app = *(TRib_movanal_app*)pJolly;
|
||||
const long numreg = rel.curr().get_long(MOVANA_NUMREG);
|
||||
TAnal_mov anal_mov(numreg);
|
||||
//se va tutto bene riscrive l'intero movimento analitico con conseguente ricalcolo saldi
|
||||
if (app.elabora_movimento(anal_mov, true))
|
||||
anal_mov.rewrite(rel.lfile());
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool compatta_callback(const TRelation& rel, void* pJolly)
|
||||
{
|
||||
TRib_movanal_app& app = *(TRib_movanal_app*)pJolly;
|
||||
const long numreg = rel.curr().get_long(MOVANA_NUMREG);
|
||||
TAnal_mov anal_mov(numreg);
|
||||
//se va tutto bene riscrive l'intero movimento analitico con conseguente ricalcolo saldi
|
||||
if (app.elabora_movimento(anal_mov, false))
|
||||
anal_mov.rewrite(rel.lfile());
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void TRib_movanal_app::main_loop()
|
||||
{
|
||||
TRib_movanal_msk mask;
|
||||
while (mask.run() == K_ENTER)
|
||||
{
|
||||
//deve scandire il file MOVANA con chiave 2 (per data e numero di registrazione)
|
||||
TRelation rel_movana(LF_MOVANA);
|
||||
TRectype darec(LF_MOVANA), arec(LF_MOVANA);
|
||||
const TDate & dal = mask.get_date(F_DATAINI);
|
||||
darec.put(MOVANA_DATACOMP, dal);
|
||||
const TDate & al = mask.get_date(F_DATAFIN);
|
||||
arec.put(MOVANA_DATACOMP, al);
|
||||
_cache_rip.set_esercizio(mask.get_int(F_ANNO));
|
||||
|
||||
const TString & tipo = mask.get(F_CLASSEMOV);
|
||||
TString filter;
|
||||
|
||||
if (tipo.blank())
|
||||
filter = "BLOCCATO!=\"X\"";
|
||||
else
|
||||
if (tipo == "N")
|
||||
filter = "(BLOCCATO!=\"X\")&&(TIPOMOV==\"\")";
|
||||
else
|
||||
filter = "(BLOCCATO!=\"X\")&&(TIPOMOV!=\"\")";
|
||||
TCursor cur_movana(&rel_movana, filter, 2, &darec, &arec);
|
||||
const long items = cur_movana.items();
|
||||
if (items > 0)
|
||||
{
|
||||
bool run = yesno_box(FR("Si desidera elaborare %ld movimenti?"), items);
|
||||
//e' una compattazione?
|
||||
const bool compattazione = mask.get_bool(F_COMPATTA);
|
||||
//se e' un ripartizione potrebbe essere definitiva!
|
||||
if (!compattazione)
|
||||
{
|
||||
// avvisa l'utente scapestrato che se fa una ripartizione definitiva
|
||||
// blocchera' i movimenti che processa e non potra' piu' tornare indietro
|
||||
_definitivo = mask.get_bool(F_DEFINITIVO);
|
||||
if (run && _definitivo)
|
||||
run = yesno_box(TR("E' stata selezionata l'elaborazione definitiva\nSi desidera proseguire?"));
|
||||
}
|
||||
|
||||
//Presa la decisione si parte! Tenetevi forte...
|
||||
if (run)
|
||||
{
|
||||
if (compattazione)
|
||||
cur_movana.scan(compatta_callback, this, TR("Compattamento movimenti..."));
|
||||
else
|
||||
cur_movana.scan(ripartisci_callback, this, TR("Ripartizione movimenti..."));
|
||||
} //if(run)...
|
||||
}
|
||||
else
|
||||
message_box(TR("Non ci sono movimenti da elaborare nel periodo selezionato"));
|
||||
}
|
||||
}
|
||||
|
||||
int pd6342300(int argc, char* argv[])
|
||||
{
|
||||
TRib_movanal_app app;
|
||||
app.run(argc, argv, TR("Ripartizione movimenti di analitica (Habilita)"));
|
||||
return 0;
|
||||
}
|
12
ps/pd6342300a.h
Executable file
12
ps/pd6342300a.h
Executable file
@ -0,0 +1,12 @@
|
||||
// campi maschera ca2200a.uml
|
||||
|
||||
#define F_DATAINI 201
|
||||
#define F_DATAFIN 202
|
||||
#define F_DEFINITIVO 203
|
||||
#define F_ANNO 204
|
||||
#define F_COMPATTA 205
|
||||
#define F_CLASSEMOV 206
|
||||
//Devono valere un numero piu' alto di S_CDC12 (che attualmente e' 112) senno' non nascono in fila nello..
|
||||
//..sheet
|
||||
#define F_CODCAUS 113
|
||||
#define F_DESCAUS 114
|
88
ps/pd6342300a.uml
Executable file
88
ps/pd6342300a.uml
Executable file
@ -0,0 +1,88 @@
|
||||
#include "pd6342300a.h"
|
||||
#include "camask.h"
|
||||
|
||||
TOOLBAR "topbar" 0 0 0 2
|
||||
|
||||
BUTTON DLG_SAVEREC 10 2
|
||||
BEGIN
|
||||
PROMPT -23 -11 "~Salva"
|
||||
PICTURE TOOL_SAVEREC
|
||||
END
|
||||
|
||||
#include <elabar.h>
|
||||
|
||||
ENDPAGE
|
||||
|
||||
TOOLBAR "" 0 -2 0 2
|
||||
|
||||
STRING DLG_PROFILE 50
|
||||
BEGIN
|
||||
PROMPT 9 -11 "Profilo "
|
||||
PSELECT
|
||||
END
|
||||
|
||||
ENDPAGE
|
||||
|
||||
PAGE "Ripartizione\Compattamento movimenti" 0 0 0 2
|
||||
|
||||
GROUPBOX DLG_NULL 78 8
|
||||
BEGIN
|
||||
PROMPT 1 1 "@bParametri di elaborazione"
|
||||
END
|
||||
|
||||
NUMBER F_ANNO 4
|
||||
BEGIN
|
||||
PROMPT 2 2 "Esercizio "
|
||||
USE ESC
|
||||
INPUT CODTAB F_ANNO
|
||||
DISPLAY "Codice Esercizio" CODTAB
|
||||
DISPLAY "Data inizio esercizio" D0
|
||||
DISPLAY "Data fine esercizio " D1
|
||||
OUTPUT F_ANNO CODTAB
|
||||
OUTPUT F_DATAINI D0
|
||||
OUTPUT F_DATAFIN D1
|
||||
CHECKTYPE REQUIRED
|
||||
FLAGS "RZ"
|
||||
ADD NONE
|
||||
END
|
||||
|
||||
LIST F_CLASSEMOV 22
|
||||
BEGIN
|
||||
PROMPT 36 2 "Classe movimento "
|
||||
ITEM " |Tutti"
|
||||
ITEM "N|Normali"
|
||||
ITEM "P|Preventivo/Variazioni"
|
||||
END
|
||||
|
||||
|
||||
|
||||
DATA F_DATAINI
|
||||
BEGIN
|
||||
PROMPT 2 3 "Dalla data "
|
||||
CHECKTYPE REQUIRED
|
||||
END
|
||||
|
||||
DATA F_DATAFIN
|
||||
BEGIN
|
||||
PROMPT 42 3 "Alla data "
|
||||
CHECKTYPE REQUIRED
|
||||
END
|
||||
|
||||
RADIOBUTTON F_COMPATTA 1 40
|
||||
BEGIN
|
||||
PROMPT 2 4 "Elaborazione richiesta"
|
||||
ITEM " |Ripartizione"
|
||||
MESSAGE ENABLE,F_DEFINITIVO
|
||||
ITEM "X|Compattamento"
|
||||
MESSAGE CLEAR,F_DEFINITIVO
|
||||
FLAGS "Z"
|
||||
END
|
||||
|
||||
BOOLEAN F_DEFINITIVO
|
||||
BEGIN
|
||||
PROMPT 2 7 "Blocca movimenti elaborati (DEFINITIVO e vale solo per ripartizione)"
|
||||
END
|
||||
|
||||
ENDPAGE
|
||||
|
||||
ENDMASK
|
Loading…
x
Reference in New Issue
Block a user