Skip to content

Commit ad0a3a5

Browse files
feat: Gestione cespiti e ammortamenti
1 parent bb98289 commit ad0a3a5

8 files changed

Lines changed: 491 additions & 9 deletions

File tree

modules/ammortamenti/actions.php

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
<?php
2+
3+
/*
4+
* OpenSTAManager: il software gestionale open source per l'assistenza tecnica e la fatturazione
5+
* Copyright (C) DevCode s.r.l.
6+
*
7+
* This program is free software: you can redistribute it and/or modify
8+
* it under the terms of the GNU General Public License as published by
9+
* the Free Software Foundation, either version 3 of the License, or
10+
* (at your option) any later version.
11+
*
12+
* This program is distributed in the hope that it will be useful,
13+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15+
* GNU General Public License for more details.
16+
*
17+
* You should have received a copy of the GNU General Public License
18+
* along with this program. If not, see <https://www.gnu.org/licenses/>.
19+
*/
20+
21+
include_once __DIR__.'/../../core.php';
22+
23+
use Modules\PrimaNota\Mastrino;
24+
use Modules\PrimaNota\Movimento;
25+
use Modules\Fatture\Components\Articolo;
26+
use Modules\Fatture\Components\Riga;
27+
use Carbon\Carbon;
28+
29+
switch (filter('op')) {
30+
case 'add_ammortamento':
31+
$id_conto = post('id_conto');
32+
$anni = (array) post('anno');
33+
$percentuale = (array) post('percentuale');
34+
35+
// Recupero informazioni sulla riga del documento
36+
$riga = Articolo::find($id_record) ?: Riga::find($id_record);
37+
$id_conto_dare = $riga->idconto;
38+
$id_conto_avere = $id_conto;
39+
40+
// Elimino i movimenti collegati agli ammortamenti precedenti
41+
$ammortamenti_precedenti = $dbo->fetchArray('SELECT * FROM `co_righe_ammortamenti` WHERE `id_riga` = '.prepare($id_record));
42+
foreach ($ammortamenti_precedenti as $ammortamento) {
43+
if (!empty($ammortamento['id_mastrino'])) {
44+
$mastrino_precedente = Mastrino::find($ammortamento['id_mastrino']);
45+
if (!empty($mastrino_precedente)) {
46+
$mastrino_precedente->delete();
47+
}
48+
}
49+
}
50+
51+
// Elimino le righe di ammortamento precedenti
52+
$dbo->query('DELETE FROM `co_righe_ammortamenti` WHERE `id_riga` = '.prepare($id_record));
53+
foreach ($anni as $i => $anno) {
54+
$perc = $percentuale[$i];
55+
56+
if ($perc) {
57+
// Calcolo importo in base alla percentuale
58+
$importo = $riga->subtotale * $perc / 100;
59+
60+
// Creazione mastrino
61+
$data = Carbon::createFromDate($anno, 12, 31);
62+
$descrizione = 'Ammortamento del '.$data->format('d/m/Y').' - '.$perc.'%';
63+
$mastrino = Mastrino::build($descrizione, $data, false, true);
64+
65+
// Movimento in dare (conto della riga)
66+
$movimento_dare = Movimento::build($mastrino, $id_conto_dare);
67+
$movimento_dare->setTotale($importo, 0);
68+
$movimento_dare->save();
69+
70+
// Movimento in avere (conto selezionato)
71+
$movimento_avere = Movimento::build($mastrino, $id_conto_avere);
72+
$movimento_avere->setTotale(0, $importo);
73+
$movimento_avere->save();
74+
75+
// Salvataggio record ammortamento
76+
$dbo->query('INSERT INTO `co_righe_ammortamenti` (`id_riga`, `anno`, `id_conto`, `percentuale`, `id_mastrino`) VALUES ('.prepare($id_record).', '.prepare($anno).', '.prepare($id_conto).', '.prepare($perc).', '.prepare($movimento_dare->idmastrino).')');
77+
}
78+
}
79+
80+
flash()->info(tr('Ammortamenti registrati con successo!'));
81+
82+
break;
83+
}

modules/ammortamenti/edit.php

Lines changed: 269 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,269 @@
1+
<?php
2+
/*
3+
* OpenSTAManager: il software gestionale open source per l'assistenza tecnica e la fatturazione
4+
* Copyright (C) DevCode s.r.l.
5+
*
6+
* This program is free software: you can redistribute it and/or modify
7+
* it under the terms of the GNU General Public License as published by
8+
* the Free Software Foundation, either version 3 of the License, or
9+
* (at your option) any later version.
10+
*
11+
* This program is distributed in the hope that it will be useful,
12+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14+
* GNU General Public License for more details.
15+
*
16+
* You should have received a copy of the GNU General Public License
17+
* along with this program. If not, see <https://www.gnu.org/licenses/>.
18+
*/
19+
20+
include_once __DIR__.'/../../core.php';
21+
22+
// Recupero informazioni sulla riga del documento
23+
$documento = $dbo->fetchOne('SELECT * FROM `co_documenti` WHERE id='.prepare($record['iddocumento']));
24+
25+
// Recupero righe di ammortamento esistenti
26+
$righe_ammortamento = $dbo->fetchArray('SELECT * FROM `co_righe_ammortamenti` WHERE id_riga='.prepare($id_record).' ORDER BY anno ASC');
27+
$numero_righe = count($righe_ammortamento);
28+
29+
// Calcola anno di inizio (anno del documento)
30+
$anno_inizio = date('Y', strtotime($documento['data_competenza']));
31+
32+
$readonly = $anno_inizio == date('Y') ? 0 : 1;
33+
34+
// Recupero conti patrimoniali
35+
$conti_patrimoniali = $dbo->fetchArray('SELECT id, descrizione FROM co_pianodeiconti2 WHERE idpianodeiconti1=(SELECT id FROM co_pianodeiconti1 WHERE descrizione="Patrimoniale") ORDER BY descrizione ASC');
36+
37+
?><form action="" method="post" id="edit-form">
38+
<input type="hidden" name="backto" value="record-edit">
39+
<input type="hidden" name="op" value="add_ammortamento">
40+
41+
<!-- DATI -->
42+
<div class="card card-primary">
43+
<div class="card-header">
44+
<h3 class="card-title"><?php echo tr('Informazioni'); ?></h3>
45+
</div>
46+
47+
<div class="card-body">
48+
<div class="row">
49+
<div class="col-md-6">
50+
{[ "type": "text", "label": "<?php echo tr('Cespite'); ?>", "name": "descrizione_riga", "value": "<?php echo $record['descrizione']; ?>", "disabled": 1 ]}
51+
</div>
52+
53+
<div class="col-md-2">
54+
{[ "type": "text", "label": "<?php echo tr('Importo'); ?>", "name": "importo_riga", "value": "<?php echo numberFormat($record['subtotale']); ?>", "disabled": 1, "class": "text-right", "icon-after": "<?php echo currency(); ?>" ]}
55+
</div>
56+
57+
<div class="col-md-4">
58+
<?php echo Modules::link('Fatture di acquisto', $documento['id'], null, null, 'class="pull-right"'); ?>
59+
{[ "type": "text", "label": "<?php echo tr('Fattura di origine'); ?>", "name": "fattura_collegata", "value": "<?php echo $documento['numero']; ?> del <?php echo dateFormat($documento['data_competenza']); ?>", "disabled": 1 ]}
60+
</div>
61+
</div>
62+
</div>
63+
</div>
64+
65+
<div class="card card-primary">
66+
<div class="card-header">
67+
<h3 class="card-title"><?php echo tr('Ammortamenti'); ?></h3>
68+
</div>
69+
70+
<div class="card-body">
71+
<div class="row">
72+
<div class="col-md-6">
73+
{[ "type": "select", "label": "<?php echo tr('Conto per ammortamento'); ?>", "name": "id_conto", "required": 1, "values": "query=SELECT co_pianodeiconti3.id, CONCAT(co_pianodeiconti2.numero, '.', co_pianodeiconti3.numero, ' - ', co_pianodeiconti3.descrizione) AS descrizione FROM co_pianodeiconti3 INNER JOIN co_pianodeiconti2 ON co_pianodeiconti3.idpianodeiconti2=co_pianodeiconti2.id WHERE idpianodeiconti2=<?php echo prepare(setting('Conto predefinito per gli ammortamenti')); ?>", "value": "<?php echo $righe_ammortamento[0]['id_conto']; ?>", "disabled": "<?php echo $readonly > 0 ? 1 : 0; ?>" ]}
74+
</div>
75+
76+
<div class="col-md-6" style="margin-top: 25px">
77+
<button type="button" class="btn btn-info pull-right <?php echo ($readonly > 0 ? 'disabled' : ''); ?>" id="add-riga">
78+
<i class="fa fa-plus"></i> <?php echo tr('Aggiungi riga'); ?>
79+
</button>
80+
</div>
81+
</div>
82+
83+
<div class="table-responsive">
84+
<table class="table table-striped table-hover table-bordered">
85+
<thead>
86+
<tr>
87+
<th class="text-center"><?php echo tr('Anno'); ?></th>
88+
<th width="30%"><?php echo tr('Percentuale'); ?></th>
89+
<th width="30%"><?php echo tr('Importo'); ?></th>
90+
<th width="15%" class="text-center"><?php echo tr('Movimento'); ?></th>
91+
</tr>
92+
</thead>
93+
<tbody id="righe-ammortamento">
94+
<?php
95+
// Righe esistenti
96+
foreach ($righe_ammortamento as $index => $riga) {
97+
echo '
98+
<tr>
99+
<td>
100+
{[ "type": "text", "name": "anno['.$riga['id'].']", "value": "'.$riga['anno'].'", "disabled": "1", "class": "text-center" ]}
101+
</td>
102+
<td>
103+
{[ "type": "number", "name": "percentuale['.$riga['id'].']", "value": "'.$riga['percentuale'].'", "icon-after": "%", "disabled": "'.$readonly.'", "class": "percentuale" ]}
104+
</td>
105+
<td>
106+
{[ "type": "number", "name": "importo['.$riga['id'].']", "value": "'.$riga['importo'].'", "icon-after": "'.currency().'", "disabled": "1", "class": "importo" ]}
107+
</td>
108+
<td class="text-center">
109+
'.($riga['id_mastrino'] ? Modules::link('Prima nota', $riga['id_mastrino'], 'Visualizza prima nota', null, 'class="btn btn-sm btn-primary"') : '').'
110+
</td>
111+
</tr>';
112+
}
113+
?>
114+
</tbody>
115+
</table>
116+
</div>
117+
118+
<div class="alert alert-warning text-center hide" id="alert-percentuale">
119+
<i class="fa fa-warning"></i> <?php echo tr('Attenzione! La somma delle percentuali deve essere esattamente 100%'); ?>
120+
<br>
121+
<?php echo tr('Totale attuale'); ?>: <span id="totale-percentuale">0</span>%
122+
</div>
123+
124+
<div class="alert alert-info text-center">
125+
<i class="fa fa-info-circle"></i> <?php echo tr('Ammortamento modificabile fino al 31/12/_ANNO_', [
126+
'_ANNO_' => $anno_inizio,
127+
]); ?>
128+
</div>
129+
130+
<div class="row">
131+
<div class="col-md-12 text-center">
132+
<button type="button" class="btn btn-lg btn-primary <?php echo ($readonly ? 'disabled' : ''); ?>" id="btn-salva" onclick="applicaAmmortamento()">
133+
<?php echo tr('Applica ammortamento'); ?>
134+
</button>
135+
</div>
136+
</div>
137+
</div>
138+
</div>
139+
</form>
140+
141+
<!-- Template per nuova riga -->
142+
<table class="hide">
143+
<tbody id="template-riga">
144+
<tr>
145+
<td>
146+
{[ "type": "text", "name": "anno[-id-]", "value": "-anno-", "disabled": 1, "class": "text-center" ]}
147+
</td>
148+
<td>
149+
{[ "type": "number", "name": "percentuale[-id-]", "value": "0", "icon-after": "%", "class": "percentuale" ]}
150+
</td>
151+
<td>
152+
{[ "type": "number", "name": "importo[-id-]", "value": "0", "icon-after": "<?php echo currency(); ?>", "disabled": "1", "class": "importo" ]}
153+
</td>
154+
<td class="text-center"></td>
155+
</tr>
156+
</tbody>
157+
</table>
158+
159+
<script>
160+
$(document).ready(function() {
161+
$("#save-buttons").hide();
162+
163+
// Variabili globali
164+
var importo_totale = <?php echo $record['subtotale']; ?>;
165+
var indice_riga = 0;
166+
var anno_documento = <?php echo $anno_inizio; ?>;
167+
var numero_righe_create = <?php echo $numero_righe; ?>;
168+
169+
// Aggiunta nuova riga
170+
$("#add-riga").click(function() {
171+
var template = $("#template-riga").html();
172+
var anno_da_usare;
173+
174+
// Se è la prima riga, usa l'anno del documento
175+
if ($("#righe-ammortamento tr").length === 0) {
176+
anno_da_usare = anno_documento;
177+
} else {
178+
// Altrimenti prendi l'anno dell'ultima riga e aggiungi 1
179+
var ultima_riga = $("#righe-ammortamento tr:last-child");
180+
var ultimo_anno = parseInt(ultima_riga.find("input[name^='anno']").val());
181+
anno_da_usare = ultimo_anno + 1;
182+
}
183+
184+
var html = template.replace(/-id-/g, indice_riga)
185+
.replace(/-anno-/g, anno_da_usare);
186+
187+
$("#righe-ammortamento").append(html);
188+
indice_riga++;
189+
190+
// Aggiorna gli importi
191+
aggiornaImporti();
192+
});
193+
194+
// Aggiornamento importi in base alla percentuale
195+
$(document).on("input", ".percentuale", function() {
196+
aggiornaImporti();
197+
});
198+
199+
// Funzione per aggiornare gli importi
200+
function aggiornaImporti() {
201+
var totale_percentuale = 0;
202+
203+
$(".percentuale").each(function() {
204+
var percentuale = parseFloat($(this).val()) || 0;
205+
var importo = (percentuale / 100) * importo_totale;
206+
207+
// Trova il campo importo corrispondente
208+
var importo_field = $(this).closest("tr").find(".importo");
209+
importo_field.val(importo);
210+
211+
totale_percentuale += percentuale;
212+
});
213+
214+
// Aggiorna il totale visualizzato
215+
$("#totale-percentuale").text(totale_percentuale.toFixed(0));
216+
217+
// Mostra o nascondi l'avviso in base al totale
218+
if (totale_percentuale != 100 && totale_percentuale != 0) {
219+
$("#alert-percentuale").removeClass("hide");
220+
} else {
221+
$("#alert-percentuale").addClass("hide");
222+
}
223+
224+
return (totale_percentuale == 100 || totale_percentuale == 0);
225+
}
226+
227+
// Inizializza gli importi
228+
aggiornaImporti();
229+
230+
// Controlla se il pulsante di salvataggio deve essere abilitato
231+
function controllaPulsanteCrea() {
232+
var totale_valido = aggiornaImporti();
233+
var righe_presenti = $("#righe-ammortamento tr").length > 0;
234+
235+
// Abilita il pulsante solo se ci sono righe e il totale è 100%
236+
if (totale_valido && righe_presenti) {
237+
$("#btn-salva").removeClass("disabled");
238+
} else {
239+
$("#btn-salva").addClass("disabled");
240+
}
241+
}
242+
243+
// Controlla lo stato del pulsante all'avvio
244+
controllaPulsanteCrea();
245+
246+
// Controlla lo stato del pulsante quando vengono modificate le percentuali
247+
$(document).on("input", ".percentuale", function() {
248+
controllaPulsanteCrea();
249+
});
250+
251+
// Controlla lo stato del pulsante quando viene aggiunta o rimossa una riga
252+
$("#add-riga").click(function() {
253+
controllaPulsanteCrea();
254+
});
255+
});
256+
257+
// Funzione per confermare l'applicazione dell'ammortamento
258+
function applicaAmmortamento() {
259+
swal({
260+
title: "<?php echo tr('Applicare l\'ammortamento?'); ?>",
261+
html: "<?php echo tr('Sei sicuro di voler applicare questo ammortamento?'); ?>",
262+
type: "success",
263+
showCancelButton: true,
264+
confirmButtonText: "<?php echo tr('Sì, procedi'); ?>"
265+
}).then(function () {
266+
$('#save').click();
267+
}).catch(swal.noop);
268+
}
269+
</script>

modules/ammortamenti/init.php

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
<?php
2+
3+
/*
4+
* OpenSTAManager: il software gestionale open source per l'assistenza tecnica e la fatturazione
5+
* Copyright (C) DevCode s.r.l.
6+
*
7+
* This program is free software: you can redistribute it and/or modify
8+
* it under the terms of the GNU General Public License as published by
9+
* the Free Software Foundation, either version 3 of the License, or
10+
* (at your option) any later version.
11+
*
12+
* This program is distributed in the hope that it will be useful,
13+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15+
* GNU General Public License for more details.
16+
*
17+
* You should have received a copy of the GNU General Public License
18+
* along with this program. If not, see <https://www.gnu.org/licenses/>.
19+
*/
20+
21+
use Models\OAuth2;
22+
23+
include_once __DIR__.'/../../core.php';
24+
25+
if (!empty($id_record)) {
26+
$record = $dbo->fetchOne('SELECT * FROM `co_righe_documenti` WHERE id='.prepare($id_record));
27+
}

0 commit comments

Comments
 (0)