// ----------------------------------------------------------------- // Calcolo liquidazione // part 4: casi particolari // fv 2-2-94 // ----------------------------------------------------------------- #include "cg4300.h" void TLiquidazione_app::add_plafond(int month, const char* codatt, int type, real& howmuch, bool intra) { look_ppa(month,codatt,type); TString att(codatt); real r0 = _ppa_r->get_real("R0"); real r1 = _ppa_r->get_real("R1"); real r2 = _ppa_r->get_real("R2"); if (intra) r1 += howmuch; else r0 += howmuch; //06/12/1995 /* if (r2 < (r0+r1)) describe_error("Acquisti in eccesso rispetto al plafond disponibile", att.cut(5)); */ //fine _ppa_r->put("R0",r0); _ppa_r->put("R1",r1); _ppa->rewrite(); } void TLiquidazione_app::zero_plafond (int month, const char* codatt) { for (int jj = 1; jj <= 3; jj++) // three types of plafond { real r; look_ppa(month,codatt,jj,TRUE); if (is_first_month(month)) { r = (jj == 1 ? _p8 : (jj == 2 ? _p8b : _p9)); } else { long rn = _ppa->recno(); // se non c'e' quello del mese prima c'e' poco da fare, // si ricalcola tutto if (!look_ppa(previous_month(month),codatt,jj)) // mazza che bella chiamata ricorsiva { if (_recalc != needed) { describe_error("Progressivi plafond non ricalcolati per " "i mesi precedenti: possibili errori", codatt); } else { if (!update_att(previous_month(month),codatt, FALSE)) describe_error("Progressivi plafond non ricalcolati per " "i mesi precedenti: possibili errori", codatt); look_ppa(previous_month(month),codatt,jj); } } r = _ppa_r->get_real("R2") - _ppa_r->get_real("R0") - _ppa_r->get_real("R1"); _ppa->readat(rn); } _ppa_r->put("R2",r); _ppa_r->put("R0",""); _ppa_r->put("R1",""); _ppa->rewrite(); } // for tipo esenzione plafond } // ricalcolo dei corrispettivi void TLiquidazione_app::recalc_corrispettivi(int month, const char* codatt) { if (_corr_arr.items() == 0) return; // ricalcola (solo per il mese in corso!) operando sull'array for (int i = 0; i < _corr_arr.items(); i++) { _CorrItem* ci = (_CorrItem*)&_corr_arr[i]; if (ci->_month != month || ci->_codatt != codatt) continue; real imposta = (abs(ci->_totale) * ci->_aliquota)/(ci->_aliquota + 1.00); imposta.ceil(); if (ci->_totale.sign() < 0) imposta = -imposta; real imponibile = ci->_totale - imposta; // quadratura del cerchione real delta = ci->_totale - imponibile - imposta; if (!delta.is_zero()) imposta += delta; // aggiusto l'IVA vendite nei plm look_plm(month, codatt); real ive = _plm->get_real("R0"); ive += imposta; _plm->put("R0",ive); _plm->rewrite(); // .. e il volume di affari nei pam real vaf = _pam->get_real("R1"); vaf += imponibile; _pam->put("R1", vaf); _pam->rewrite(); // Aggiorno i luridi pim look_pim(month, codatt, ci->_codreg, "", ci->_codiva, ci->_tipodet, TRUE); imponibile += _pim->get_real("R0"); imposta += _pim->get_real("R1"); _pim->put("R0", imponibile); _pim->put("R1", imposta); _pim->rewrite(); } } // ricalcolo della malefica ventilazione void TLiquidazione_app::recalc_ventilation(int month, const char* codatt) { if (!_isvent || _isagricolo || _isviaggio || _vend_arr.items() == 0) return; TString att(codatt); // 1) ricalcola i pim dei mesi dal primo al corrente se necessario recalc rcl = _recalc; _recalc = needed; for (int m = 1; m < month; m++) update_att(m,codatt, FALSE); _recalc = rcl; _vent_arr.destroy(); for (m = 1; m <= month; m++) { // aggiunge gli acquisti del mese m operando sui pim for (_pim->first(); !_pim->eof(); _pim->next()) { if (_year != *_pim_anno) continue; // se e' acquisto beni per rivendita int tipocr = atoi(*_pim_tipocr); int mese = atoi(*_pim_mese); int tipodet = atoi(*_pim_tipodet); look_iva(*_pim_codiva); // base di riparto solo se non esente, non soggetto, non imponibile TString16 tipoiva(_iva->get("S1")); TString16 reg = *_pim_codreg; /* * caso particolare SENSU Vladimiro (1995) #MI3001 * questi vengono pero' conteggiati nel totale * acquisti per rivendita */ if (tipocr == 5 && tipodet == 3) continue; TString att(codatt); if (tipocr == 1 && (mese == m) && att == (const char*)(*_pim_codatt)) { if (tipoiva != "NS" && tipoiva != "NI" && tipoiva != "ES") { real lurd = _pim->get_real("R0"); lurd += _pim->get_real("R1"); real perc = _iva->get_real("R0"); TString other = _iva->get("S6"); if (!other.empty()) { // ventila a un altro codice look_iva(other); perc = _iva->get_real("R0"); } add_ventilation(perc / CENTO, lurd, *_pim_codiva, other); } } } } // 2) calcola totale acquisti su tutte le aliquote real totacq = 0.0; real totven = 0.0; for (int j = 0; j < _vent_arr.items(); j++) { _VentItem& vv = (_VentItem&)_vent_arr[j]; totacq += vv._totale; } // 3) ricalcola (solo per il mese in corso!) operando sull'array for (int i = 0; i < _vend_arr.items(); i++) { _VendItem* vi = (_VendItem*)&_vend_arr[i]; if (vi->_month != month) continue; // questo serve solo per il prospettino di m. totven += vi->_totale; // 3.2) calcola percentuali di ripartizione e prepara l'affettatrice TDistrib dst(vi->_totale,ROUND_LIRA); for (j = 0; j < _vent_arr.items(); j++) { _VentItem* vv = (_VentItem*)&_vent_arr[j]; dst.add(vv->_totale/totacq); } // 3.3) affetta l'importo real tlor = 0.0; for (j = 0; j < _vent_arr.items(); j++) { _VentItem* vv = (_VentItem*)&_vent_arr[j]; real imponibile = dst.get(); real div(1.0); div += vv->_aliquota; real totale = imponibile; real imposta = imponibile - (imponibile/div); imposta.ceil(ROUND_LIRA); imponibile -= imposta; // quadratura del cerchione real delta = totale - imponibile - imposta; if (!delta.is_zero()) imposta += delta; tlor += imponibile + imposta; // quadratura generale (solo per unita', che peraltro // dovrebbe essere l'unica possibile stronzata if ((totven - tlor) == real(1.0)) imposta += real(1.0); // aggiusto l'IVA vendite nei plm look_plm(month, codatt); real ive = _plm->get_real("R0"); ive += imposta; _plm->put("R0",ive); _plm->rewrite(); // .. e il volume di affari nei pam real vaf = _pam->get_real("R1"); vaf += imponibile; _pam->put("R1", vaf); _pam->rewrite(); // Aggiorno i luridi pim bool was = look_pim(month, codatt, vi->_codreg, "0", vv->_codiva, vi->_tipodet, TRUE); imponibile += _pim->get_real("R0"); imposta += _pim->get_real("R1"); _pim->put("R0", imponibile); _pim->put("R1", imposta); _pim->put("S4", vv->_other); // segnale per comodita' in stampa prospetto _pim->put("B1","X"); // se e' nuovo, il segnale per usare l'importo nel calcolo del rimborso // viene amorosamente messo a quanto il codice IVA prevede if (!was) { look_iva(vv->_codiva); _pim->put("I1", (long)vendita); if (!_iva->get_bool("B4")) _pim->put("B3", "X"); } _pim->rewrite(); } } // memorizza totali per il prospettino di m. look_plm(month, codatt); // PAM e PUM _pam->put("R2",totacq); _pam->put("R3",totven); _pam->rewrite(); } // questa servIVA per il rimborso secondo le // nuove cazzonorme, mai entrate in vigore ma // devotamente programmate //class rObj : public TObject //{ //public: // real _imp; // real _iva; // real _perc; // // rObj() {} // virtual ~rObj() {} //}; // defines per stabilire quale cazzo di metodo piace oggi alla prassi // ------------------------------------------------------------------ // Considera tutti i mesi del trimestre fino a quello indicato // se lasciato indefinito usa solo il mese passato #define OGGI_GLI_TIRA_DI_USARE_TRE_MESI _DescrItem* TLiquidazione_app::recalc_rimborso(int month, const char* codatts, bool stliq) { // calcola condizioni per il diritto al rimborso infracazzuale // chiamata soltanto per i trimestri anche se annuale // aggiornata a normative per anno liq. > 1994 bool rimborsami = FALSE; _DescrItem* d = NULL; TToken_string atts(codatts); const char* tmpatt; TString att; real es_ni = 0.0; real vol_aff = 0.0;; while ((tmpatt = atts.get()) != NULL) { att = tmpatt; #ifdef OGGI_GLI_TIRA_DI_USARE_TRE_MESI for (int m = (month == 13 ? 1 : (next_trim(month)-2)); m <= month; m++) { #else int m = month; #endif if (!look_plm(m,att)) continue; vol_aff += _pam->get_real("R1"); es_ni += _pum->get_real("R12"); #ifdef OGGI_GLI_TIRA_DI_USARE_TRE_MESI } #endif } // condizione 1 real prc = es_ni/vol_aff; prc.round(2); if (stliq && !vol_aff.is_zero() && prc > MIN_PARTE_ESENTE) { rimborsami = TRUE; d = new _DescrItem(RIMBORSO); d->_f0 = TRUE; d->_r0 = es_ni; d->_r1 = vol_aff; } // ---------------------- condizione 2 // u' casinu pazzescu d'u nuiu guvernu real vtot = 0.0; real atot = 0.0; real ivav = 0.0; real ivaa = 0.0; real alv = 0.0; // aliquota media vendite real ala = 0.0; // aliquota media acquisti /*********************************************************************** Sembra che sia stato annullato subito dopo che ho finito di scrivere queste 150 righe di casino *********************************************************************** // due array dove ficcare i totali per // codiva in ordine di imponibile TArray varr, aarr; // scorri i bellissimi progressivi mensili rimborso for (_rmb->first(); !_rmb->eof(); _rmb->next()) { int year = atoi((const char*)_year); int ryear = atoi((const char*)(*_rmb_anno)); int rmese = atoi((const char*)(*_rmb_mese)); if (year != ryear || (rmese < (month - 2) || rmese > month)) continue; real imp = _rmb->get("R0"); real iva = _rmb->get("R1"); real per = _rmb->get("R2"); rObj* rb = new rObj; rb->_imp = imp; rb->_iva = iva; rb->_perc = per; TArray& arr = (tiporeg)atoi((const char*)(*_rmb_tiporeg)) == vendita ? varr : aarr; for (int i = 0; i < arr.items(); i++) { rObj& robj = (rObj&)arr[i]; if (robj._imp < imp) break; } arr.insert(rb, i); // totali imponibili if ((tiporeg)atoi((const char*)(*_rmb_tiporeg)) == vendita) vtot += imp; else atot += imp; } // se ci sono due o piu' imponibili uguali devo // sostituire l'imposta con la media delle aliquote // ciclo uguale sui due array for (int w = 0; w < 2; w++) { TArray& arr = w == 0 ? varr : aarr; for (int i = 0; i < arr.items(); i++) { rObj& robj = (rObj&)arr[i]; real impref = robj._imp; real perc = robj._perc; for (int j = i+1; j < arr.items(); j++) { rObj& rbj = (rObj&)arr[j]; if (rbj._imp != impref) break; perc += rbj._perc; } // riaggiustesbimo if (j > i+1) { // funzionerebbe comunque ma risparmiamo una // divisione per 1 real ndiv(j-i); perc /= ndiv; for (; i < j; i++) { rObj& rbj = (rObj&)arr[i]; rbj._iva = rbj._imp * (perc/CENTO); rbj._iva.round(ROUND_LIRA); } i --; } } } // 51 per cento vtot *= PERC_IMP_RIMBORSABILE; atot *= PERC_IMP_RIMBORSABILE; for (w = 0; w < 2; w++) { TArray& arr = w == 0 ? varr : aarr; real timp = w == 0 ? vtot : atot; real tiva = 0.0; for (int i = 0; i < arr.items(); i++) { rObj& robj = (rObj&)arr[i]; if (timp >= robj._imp) { tiva += robj._iva; timp -= robj._imp; } else { real perc = timp/robj._imp; if (!perc.is_zero()) { real ttiv = robj._iva * perc; ttiv.round(ROUND_LIRA); tiva += ttiv; } break; } } if (w == 0) ivav = tiva; else ivaa = tiva; } **************************************************************************/ // scorri i bellissimi progressivi mensili for (_pim->first(); !_pim->eof(); _pim->next()) { int year = atoi((const char*)_year); int ryear = atoi(*_pim_anno); int rmese = atoi(*_pim_mese); // B3 significa che e' acq. o vendita valido per rimb. per aliquota if (!_pim->get_bool("B3")) continue; #ifdef OGGI_GLI_TIRA_DI_USARE_TRE_MESI if (year != ryear || (month != 13 && (rmese < (next_trim(month)-2) || rmese > month))) continue; #else if (year != ryear || (month != rmese)) continue; #endif int tipomov = (tiporeg)_pim->get_long("I1"); real imp = _pim->get("R0"); real iva = _pim->get("R1"); // totali imponibili if (tipomov == vendita) { vtot += imp; ivav += iva; } else { atot += imp; ivaa += iva; } } // finalmente alv = ivav/vtot; alv.round(4); ala = ivaa/atot; ala.round(4); // vedi condizioni rimborsami = ala > alv; if (rimborsami) { // vedi di quanto ala eccede alv; deve essere > 10% real ecc = ((ala/alv) - real(1.0)); rimborsami = (ecc >= SOGLIA_MAGGIORE_ALIQUOTA_DEL_CAZZO_PER_AVER_DIRITTO_AL_RIMBORSO); } if (stliq && rimborsami) { if (d == NULL) d = new _DescrItem(RIMBORSO); d->_f1 = TRUE; d->_r2 = vtot; d->_r3 = atot; d->_r4 = ivav; d->_r5 = ivaa; d->_r6 = alv * CENTO; d->_r7 = ala * CENTO; } if (rimborsami && is_month_ok_strict(month)) { look_lim(month); _lim->put("B2", "X"); _lim->rewrite(); } return d; }