diff --git a/.vscode/settings.json b/.vscode/settings.json
new file mode 100644
index 0000000000000000000000000000000000000000..7c3b1b378ab8d7274450b91ae6e247ddf725121f
--- /dev/null
+++ b/.vscode/settings.json
@@ -0,0 +1,49 @@
+{
+    "files.associations": {
+        "array": "cpp",
+        "atomic": "cpp",
+        "bit": "cpp",
+        "*.tcc": "cpp",
+        "cctype": "cpp",
+        "clocale": "cpp",
+        "cmath": "cpp",
+        "cstdarg": "cpp",
+        "cstddef": "cpp",
+        "cstdint": "cpp",
+        "cstdio": "cpp",
+        "cstdlib": "cpp",
+        "cwchar": "cpp",
+        "cwctype": "cpp",
+        "deque": "cpp",
+        "map": "cpp",
+        "unordered_map": "cpp",
+        "vector": "cpp",
+        "exception": "cpp",
+        "algorithm": "cpp",
+        "functional": "cpp",
+        "iterator": "cpp",
+        "memory": "cpp",
+        "memory_resource": "cpp",
+        "numeric": "cpp",
+        "optional": "cpp",
+        "random": "cpp",
+        "string": "cpp",
+        "string_view": "cpp",
+        "system_error": "cpp",
+        "tuple": "cpp",
+        "type_traits": "cpp",
+        "utility": "cpp",
+        "fstream": "cpp",
+        "initializer_list": "cpp",
+        "iosfwd": "cpp",
+        "iostream": "cpp",
+        "istream": "cpp",
+        "limits": "cpp",
+        "new": "cpp",
+        "ostream": "cpp",
+        "sstream": "cpp",
+        "stdexcept": "cpp",
+        "streambuf": "cpp",
+        "typeinfo": "cpp"
+    }
+}
\ No newline at end of file
diff --git a/all_info_fits.py b/all_info_fits.py
index a1a9e7a093e0ee3b0017afab8a9c588aa00d221c..d5e6d884b95f7641fdb3a2c9e274e4fb586c6134 100644
--- a/all_info_fits.py
+++ b/all_info_fits.py
@@ -1,10 +1,11 @@
-#printa tutte le info di un file fits
-#sostituisci il path del file .fits
-
 from astropy.io import fits
+import numpy as np
+
+# Configura numpy per visualizzare tutti i dati senza troncamenti
+np.set_printoptions(threshold=np.inf)
 
 # Percorso del file FITS
-file_path = '/home/alfonso/Scrivania/THESEUS/XGIS-X_0deg_reqEOL_v8.rmf'
+file_path = '/home/alfonso/Scrivania/THESEUS/xgis_m7-main/msk_55_4752313.fits'
 
 # Apri il file FITS
 with fits.open(file_path) as hdul:
@@ -12,8 +13,9 @@ with fits.open(file_path) as hdul:
     hdul.info()
     
     # Itera su tutte le HDU e stampa l'header e i dati
-    for hdu in hdul:
-        print(f"\nHeader HDU {hdul.index(hdu)}:")
+    for idx, hdu in enumerate(hdul):
+        print(f"\nHeader HDU {idx}:")
         print(hdu.header)
         print("\nDati:")
-        print(hdu.data)
+        print(hdu.data)  # Stampa i dati completi senza troncamenti
+
diff --git a/detector_params.inp b/detector_params.inp
index 87b086ad2686f0086ce4264fc3861e4896611dba..9f564f66bfcf518ebca722a19fc75048dc1cab0d 100644
--- a/detector_params.inp
+++ b/detector_params.inp
@@ -11,9 +11,9 @@ BUS_THICK			    = 20.				    # Bottom bus dummy thickness (in cm)
 BUS_HEIGHT			    = 150.				    # Spacecraft bus height (in cm)
 BUS_SIDE			    = 100.				    # Spacecraft bus side (in cm)
 SDD_THICK				= 450.0				    # SDD thickness (in um)
-MASK_X					= 56.1				    # X side of the coded mask (in cm)
-MASK_Y					= 56.1				    # Y side of the coded mask (in cm)
-MASK_THICK				= 1000.				    # Thickness of the coded mask (in um)
+MASK_X					= 56.5	                # X side of the coded mask (in cm) # 56.1 old
+MASK_Y					= 56.5		            # Y side of the coded mask (in cm)
+MASK_THICK				= 500.		            # Thickness of the coded mask (in um) # 1000 old
 MASK_FOCAL				= 63.				    # Focal distance btw. mask and detector (in cm)
 COLL_UPPER_1_THICK	    = 1000.0				# Upper internal collimator thickness (in um)
 COLL_UPPER_2_THICK	    = 250.0				    # Upper external collimator thickness (in um)
@@ -23,7 +23,7 @@ OPTICAL_COUPLER_THICK	= 1.0				    # Optical coupler thickness (in mm)
 # Module parameters                          
 N_SIDE					= 89				    # Number of scintillator bars per side (89x89=7921-81)
 N_SLICES_PER_BAR		= 1				    	# Number of voxels (slices) for each scintillator bar
-N_MASK_ELEM_PER_SIDE	= 16				    # Number of mask elements per side (+16 vuoti)
+N_MASK_ELEM_PER_SIDE	= 55	                # Number of mask elements per side #16 old
 
 
 # Materials
diff --git a/include/MaskParameterisation.hh b/include/MaskParameterisation.hh
index 0816daee6d4387528be57ab62bdcbb390d990df8..46b5df6256d0f969c280d9a6b36a0f7a53270d69 100644
--- a/include/MaskParameterisation.hh
+++ b/include/MaskParameterisation.hh
@@ -4,6 +4,11 @@
 #include "globals.hh"
 #include "G4VPVParameterisation.hh"
 
+#include "G4ThreeVector.hh"
+#include <vector>
+#include <utility>
+#include <string>
+
 class G4VPhysicalVolume;
 class G4Box;
 
@@ -25,12 +30,13 @@ class G4BREPSolidPolyhedra;
 class MaskParameterisation : public G4VPVParameterisation
 { 
     public:
-        MaskParameterisation(G4double, G4double, G4int);
+        MaskParameterisation(G4double side_length_X, G4double side_length_Y, G4int n_side, G4double gap, const std::string& filename);
 
         virtual	~MaskParameterisation();
 
-        void ComputeTransformation (const G4int copyNo, G4VPhysicalVolume* physVol) const;
-    
+        void ComputeTransformation (const G4int copyNo, G4VPhysicalVolume* physVol) const override;
+
+        int GetTotalZeros() const;
 
     private:  // Dummy declarations to get rid of warnings...
         void ComputeDimensions (G4Trd&,const G4int,const G4VPhysicalVolume*) const {}
@@ -50,7 +56,12 @@ class MaskParameterisation : public G4VPVParameterisation
     private:
         G4double fSideX;
         G4double fSideY;
+        G4double fGap;
         G4int nSide;
+        std::vector<std::pair<int, int>> zeroPositions;
+
+        int LoadZeroPositions(const std::string& filename);
+
 };
 
 
diff --git a/python/a.out b/python/a.out
new file mode 100755
index 0000000000000000000000000000000000000000..67b98a4d229102453ed94ee2a9591fbce78cb5a2
Binary files /dev/null and b/python/a.out differ
diff --git a/python/aeFF.py b/python/aeFF.py
index e07523ee65be4db676a36ceb7a56dcc690010b7e..2f800aeaa5ae76f1b003477770f586146d214bb2 100644
--- a/python/aeFF.py
+++ b/python/aeFF.py
@@ -1,4 +1,5 @@
 # come faccio a sapere se il mio codice è robusto
+# aEFF deve essere corretta nei dati
 
 import numpy as np
 import sys
@@ -44,18 +45,15 @@ def main():
         S_en_dep_file_filtered = S_en_dep_file[mask]
         
         # Salva i dati per il plot
-        plot_data_X.append((energy_filtered, ratio_X_filtered, theta_val, phi_val))
-        plot_data_S.append((energy_filtered, ratio_S_filtered, theta_val, phi_val))
+        #plot_data_X.append((energy_filtered, ratio_X_filtered, theta_val, phi_val))
+        #plot_data_S.append((energy_filtered, ratio_S_filtered, theta_val, phi_val))
 
         # 3 ARF
         #arf_file(energy_filtered, ratio_X_filtered, ratio_S_filtered, theta_val, phi_val)
 
         # 4 RMF
-        #print(energy_filtered)
-        #print(theta_val)
-        #print(phi_val)
-        rmf_file(energy_filtered, 'X', X_en_dep_file_filtered, theta_val, phi_val)
-        rmf_file(energy_filtered, 'S', S_en_dep_file_filtered, theta_val, phi_val)
+        #rmf_file(energy_filtered, 'X', X_en_dep_file_filtered, theta_val, phi_val)
+        #rmf_file(energy_filtered, 'S', S_en_dep_file_filtered, theta_val, phi_val)
 
         # approcci diversi per arf e rmf
         # in arf essendo più semplice la chiamo una volta e dentro scrivo due volte le cose che deve fare
diff --git a/python/areaEfficace.arf b/python/areaEfficace.arf
deleted file mode 100644
index 16f5c4044f76926fd5a7af88716f011a1521cd18..0000000000000000000000000000000000000000
Binary files a/python/areaEfficace.arf and /dev/null differ
diff --git a/python/convertFits2Ascii.py b/python/convertFits2Ascii.py
new file mode 100644
index 0000000000000000000000000000000000000000..0d33c62affe30998ecde6bab9c598c5204456005
--- /dev/null
+++ b/python/convertFits2Ascii.py
@@ -0,0 +1,30 @@
+import astropy.io.fits as fits
+import numpy as np
+
+# ! posso anche lanciare questo script dal bash iniziale e gli do come argomento il nome del file
+
+mask_file_fits = "msk_55_4752313.fits"
+
+def fits_to_ascii(mask_file_fits, mask_file_ascii):
+    
+    with fits.open(mask_file_fits) as hdul:
+        data = hdul[0].data
+
+        # Estrarre l'HDU primaria (dati e header)
+        primary_hdu = hdul[0]
+        data = primary_hdu.data
+        header = hdul[0].header
+
+        # Scrivi l'header e i dati in un file ASCII
+        with open(mask_file_ascii, 'w') as f:
+            # Scrivi l'header come commento
+            f.write("# Header Information\n")
+            for key, value in header.items():
+                f.write(f"# {key} = {value}\n")
+            f.write("# Data 0 = pieno 1 = vuoto\n")
+            
+            # Scrivi i dati matrice nel file ASCII
+            np.savetxt(f, data, fmt="%d", delimiter=" ")
+
+# Esegui la funzione specificando il file FITS di input e il file ASCII di output
+fits_to_ascii('/home/alfonso/Scrivania/THESEUS/xgis_m7-main/python/msk_55_4752313.fits', 'mask.dat')
\ No newline at end of file
diff --git a/python/data.py b/python/data.py
index bf3e17e4ca2f0e7374402391062e9e1a652b19de..3f0c28217a745c24fc8bf2ba209b0ef05b371710 100644
--- a/python/data.py
+++ b/python/data.py
@@ -3,6 +3,9 @@ import numpy as np
 from multiprocessing import Pool
 import astropy.io.fits as fits
 
+from noisy import add_noise_X, add_noise_S
+
+
 # Funzione che prende in input un singolo file FITS da processare.
 def get_data(files):
     # Estrazione di energia, theta e phi dal nome del file
@@ -27,12 +30,19 @@ def get_data(files):
         ratio_X = eventi_X/tot_events
         ratio_S = eventi_S/tot_events
         
+        X_en_dep_noisy = [add_noise_X(X_dep) for X_dep in X_en_dep]
+        S_en_dep_noisy = [add_noise_S(S_dep) for S_dep in S_en_dep]
+        
     return energy, ratio_X, ratio_S, theta, phi, X_en_dep, S_en_dep
 
 def write_results(file_dat, results):
+    
     npy_dir = "/home/alfonso/Scrivania/THESEUS/xgis_m7-main/python/npy"
+    npy_noise_dir = "/home/alfonso/Scrivania/THESEUS/xgis_m7-main/python/npy_noise"
     if not os.path.exists(npy_dir):
         os.makedirs(npy_dir)
+    if not os.path.exists(npy_noise_dir):
+        os.makedirs(npy_noise_dir)
     
     with open(file_dat, "w") as f:
         for energy, ratio_X, ratio_S, theta, phi, X_en_dep, S_en_dep in results:
@@ -48,6 +58,14 @@ def write_results(file_dat, results):
             
             f.write(f"{energy:.1f}\t{ratio_X:.3f}\t{ratio_S:.3f}\t{theta}\t{phi}\t{X_npy_file}\t{S_npy_file}\n")
 
+    # Add noise to Energy Depoists Files and save in another folder
+    npy_noise_dir = "/home/alfonso/Scrivania/THESEUS/xgis_m7-main/python/npy_noise"
+    if not os.path.exists(npy_noise_dir):
+        os.makedirs(npy_noise_dir)
+    
+    add_noise_X()
+    add_noise_S()
+
 # Estrae i dati, processa in parallelo tutti i file .fits presenti nella folder, usa le due funzioni già definite
 def data_estraction(file_dat):
     # Crea una lista di file FITS trovati nella folder. Sorted per leggerli in ordine
diff --git a/python/noisy.py b/python/noisy.py
new file mode 100644
index 0000000000000000000000000000000000000000..7e70bfe1f8f96ff870ff52b4dc4f93058445380c
--- /dev/null
+++ b/python/noisy.py
@@ -0,0 +1,85 @@
+import os
+import numpy as np
+import matplotlib.pyplot as plt
+
+
+def add_noise_X(input):
+    
+    
+    
+    w = 3.66 # eV/e-
+    fano_factor = 0.125 # for semiconductor detectors
+    sigma_fano = np.sqrt(fano_factor*input/w)   # keV*(e-)/eV -> e-rms
+    sigma_el = 30.0 # e- rms in termini di devizaioni standard
+    
+    variance = sigma_fano**2 + sigma_el**2  # Varianza della gaussiana
+    std_row = np.sqrt(variance)
+    std = (std_row*3.66)/1000     # (e-rms)*eV/(e-rms) --> keV
+
+    # Estrai un valore campionato dalla distribuzione gaussiana
+    output = np.random.normal(loc=input, scale=std)
+    #print(std)
+    #print("Valore estratto dalla distribuzione gaussiana:", output)
+    
+    
+    os.chdir("/home/alfonso/Scrivania/THESEUS/xgis_m7-main/python/npy")
+    array = np.load("X_en_dep_2.0_0.0_0.0.npy")
+    #print(array)
+
+    dep = [add_noise(input) for input in array] # list comprehension di Python, una struttura compatta che consente di applicare una funzione a ciascun elemento di un array o di una lista, creando direttamente un nuovo array con i risultati.
+
+
+
+
+    X_npy_noise_file = "X_en_dep_noy_2.0_0.0_0.0.npy"
+    X_en_dep_noise_file = os.path.join(npy_noise_dir, X_npy_noise_file)
+
+    new = np.save(X_en_dep_noise_file, dep)
+
+    loaded_dep = np.load(X_en_dep_noise_file)
+    print("Contenuto del nuovo file .npy con rumore aggiunto:")
+    print(loaded_dep)
+    
+    
+
+
+
+
+def add_noise_S(input):
+    
+    light_efficiency = 25 # e-/keV
+    sigma_stat = input*light_efficiency
+    sigma_el = 30.0 # conto due volte perche ho due sdd
+    
+    variance = sigma_stat**2 + 2*sigma_el**2
+    
+    std = np.sqrt(variance)
+    
+    # Estrai un valore campionato dalla distribuzione gaussiana
+    output = np.random.normal(loc=input, scale=std)
+    #print(std)
+    #print("Valore estratto dalla distribuzione gaussiana:", output)
+
+
+    return output
+    
+
+
+
+
+
+    # # PLOT
+    # # Genera i valori per la curva gaussiana
+    # x = np.linspace(input - 4*std, input + 4*std, 1000)
+    # y = (1 / (std * np.sqrt(2 * np.pi))) * np.exp(-0.5 * ((x - input) / std)**2)
+    # # Plot della distribuzione gaussiana
+    # plt.plot(x, y, label="Distribuzione Gaussiana", color="blue")
+    # plt.axvline(output, color="red", linestyle="--", label=f"Valore campionato: {output:.2f}")
+    # # Aggiungi etichette e titolo
+    # plt.xlabel("Valori")
+    # plt.ylabel("Densità di probabilità")
+    # plt.title("Distribuzione Gaussiana con valore campionato evidenziato")
+    # plt.legend()
+    # plt.grid()
+    # # Mostra il grafico
+    # plt.show()
diff --git a/python/rmf.py b/python/rmf.py
index c064e45c613c6e23a3048b05aa11bb787b0a3deb..810bee27c03d7dda71e8e432fdc5647436f1460e 100644
--- a/python/rmf.py
+++ b/python/rmf.py
@@ -3,50 +3,49 @@ import os
 import sys
 import numpy as np
 
-    
-def create_ebounds_header(extension):
-    extension.header['EXTNAME'] = 'EBOUNDS'
+
+def create_matrix_header(extension):
+    extension.header['EXTNAME'] = 'MATRIX'
     extension.header['TELESCOP'] = 'THESEUS'
     extension.header['INSTRUME'] = 'XGIS'
     extension.header['FILTER'] = 'NONE'
     extension.header['CHANTYPE'] = 'PHA' # PI 
-    extension.header['DETCHANS'] = 'NONE' # the total number of raw detector PHA channels in the full (uncompressed) matrix
+    extension.header['DETCHANS'] = '31' # = bins, # the total number of raw detector PHA channels in the full (uncompressed) matrix.
     extension.header['HDUCLASS'] = 'OGIP'
     extension.header['HDUCLAS1'] = 'RESPONSE'
-    extension.header['HDUCLAS2'] = 'EBOUNDS'
-    extension.header['HDUVERS'] = '1.2.0'
+    extension.header['HDUCLAS2'] = 'RSP_MATRIX'
+    extension.header['HDUVERS'] = '1.3.0'
+    #extension.header['TLMIN#'] = 'NONE'# the first channel in the response. # is the column number for the F_CHAN column (see below).
     # optional
+    #extension.header['NUMGRP'] = 'NONE' # the total number of channel subsets. The sum of the N_GRP column.
+    #extension.header['NUMELT'] = 'NONE' # the total number of response elements. The sum of the N_CHAN column
     #extension.header['PHAFILE'] = 'NONE' # name of PHA file for which this file was produced
+    extension.header['LO_THRES '] = '0.0' # minimum probability threshold used to construct the matrix (matrix elements below this value are considered to zero and are not stored)
+    extension.header['HDUCLAS3'] = 'REDIST' # giving further details of the stored matrix Allowed values are: 'REDIST' for a matrix whose elements represent probabilities associated with the photon redistribution process only 'DETECTOR' for a matrix whose elements have been multiplied by all energy-dependent effects associated with detector (eg detector efficiency, window transmission etc). 'FULL' for a matrix whose elements have been multiplied by all energy-dependent effects associated with detector, optics, collimator, filters etc.
     # obsolete (for old software)
     extension.header['RMFVERSN'] = '1992A'
     extension.header['HDUVERS1'] = '1.0.0'
-    extension.header['HDUVERS2'] = '1.1.0'  
-
-
-def create_matrix_header(extension):
-    extension.header['EXTNAME'] = 'SPECRESP MATRIX'
+    extension.header['HDUVERS2'] = '1.3.0'
+    
+    
+def create_ebounds_header(extension):
+    extension.header['EXTNAME'] = 'EBOUNDS'
     extension.header['TELESCOP'] = 'THESEUS'
     extension.header['INSTRUME'] = 'XGIS'
     extension.header['FILTER'] = 'NONE'
     extension.header['CHANTYPE'] = 'PHA' # PI 
-    extension.header['DETCHANS'] = 'NONE' # the total number of raw detector PHA channels in the full (uncompressed) matrix.
+    extension.header['DETCHANS'] = '31' # = bins, the total number of raw detector PHA channels in the full (uncompressed) matrix
     extension.header['HDUCLASS'] = 'OGIP'
     extension.header['HDUCLAS1'] = 'RESPONSE'
-    extension.header['HDUCLAS2'] = 'RSP_MATRIX'
-    extension.header['HDUVERS'] = '1.3.0'
-    #extension.header['TLMIN#'] = 'NONE'# the first channel in the response. # is the column number for the F_CHAN column (see below).
+    extension.header['HDUCLAS2'] = 'EBOUNDS'
+    extension.header['HDUVERS'] = '1.2.0'
     # optional
-    #extension.header['NUMGRP'] = 'NONE' # the total number of channel subsets. The sum of the N_GRP column.
-    #extension.header['NUMELT'] = 'NONE' # the total number of response elements. The sum of the N_CHAN column
     #extension.header['PHAFILE'] = 'NONE' # name of PHA file for which this file was produced
-    extension.header['LO_THRES '] = '0' # minimum probability threshold used to construct the matrix (matrix elements below this value are considered to zero and are not stored)
-    extension.header['HDUCLAS3'] = 'REDIST' # giving further details of the stored matrix Allowed values are: 'REDIST' for a matrix whose elements represent probabilities associated with the photon redistribution process only 'DETECTOR' for a matrix whose elements have been multiplied by all energy-dependent effects associated with detector (eg detector efficiency, window transmission etc). 'FULL' for a matrix whose elements have been multiplied by all energy-dependent effects associated with detector, optics, collimator, filters etc.
     # obsolete (for old software)
     extension.header['RMFVERSN'] = '1992A'
     extension.header['HDUVERS1'] = '1.0.0'
-    extension.header['HDUVERS2'] = '1.3.0'
-    
-    # altre mandatory che non ho capito
+    extension.header['HDUVERS2'] = '1.1.0'
+
 
 def estract_row(en_dep_file, bins):
     
@@ -87,6 +86,7 @@ def estract_row(en_dep_file, bins):
     
     return n_grp, f_chan, n_chan, counts_norm       # row_matrix = counts_norm
 
+
 def rmf_file(energy, type, en_dep_file_filt, theta, phi):
     try:
         os.chdir("/home/alfonso/Scrivania/THESEUS/xgis_m7-main/python/npy")
@@ -121,14 +121,6 @@ def rmf_file(energy, type, en_dep_file_filt, theta, phi):
         # Creazione di "Null" primary array
         primary_hdu = pyfits.PrimaryHDU()
         
-        # Creazione di ebounds BinTableHDU
-        ebounds_bin_table_hdu = pyfits.BinTableHDU.from_columns([
-            pyfits.Column(name='CHANNEL', format='1I', array = channels),
-            pyfits.Column(name='E_MIN', format='1E', unit='keV', array = bins[:-1]),           
-            pyfits.Column(name='E_MAX', format='1E', unit='keV', array = bins[1:]),      
-            ])
-        create_ebounds_header(ebounds_bin_table_hdu)
-        
         # Creazione di matrice BinTableHDU
         matrix_bin_table_hdu = pyfits.BinTableHDU.from_columns([
             pyfits.Column(name='ENERG_LO', format='1E', unit='keV', array = energy[:-1]),          
@@ -140,8 +132,16 @@ def rmf_file(energy, type, en_dep_file_filt, theta, phi):
         ])
         create_matrix_header(matrix_bin_table_hdu)
         
+        # Creazione di ebounds BinTableHDU
+        ebounds_bin_table_hdu = pyfits.BinTableHDU.from_columns([
+            pyfits.Column(name='CHANNEL', format='1I', array = channels),
+            pyfits.Column(name='E_MIN', format='1E', unit='keV', array = bins[:-1]),           
+            pyfits.Column(name='E_MAX', format='1E', unit='keV', array = bins[1:]),      
+            ])
+        create_ebounds_header(ebounds_bin_table_hdu)
+        
         # Creazione di HDUList e scrittura del file FITS
-        hdul = pyfits.HDUList([primary_hdu, ebounds_bin_table_hdu, matrix_bin_table_hdu])
+        hdul = pyfits.HDUList([primary_hdu, matrix_bin_table_hdu, ebounds_bin_table_hdu])
         
         # ! *************************************************************************************************************
 
diff --git a/python/zero.CANCELLA.py b/python/zero.CANCELLA.py
new file mode 100644
index 0000000000000000000000000000000000000000..abd69086dae30b04a6a88310c486a1aa0efa50ed
--- /dev/null
+++ b/python/zero.CANCELLA.py
@@ -0,0 +1,16 @@
+# Nome del file da leggere
+file_path = "mask.dat"
+
+# Apri il file in modalità lettura
+with open(file_path, 'r') as file:
+    # Itera su ogni riga del file
+    for line_num, line in enumerate(file, start=1):
+        # Rimuovi eventuali spazi vuoti ai bordi e dividi la riga in elementi
+        elements = line.strip().split()
+        
+        # Conta il numero di '0' nella riga corrente
+        zero_count = elements.count('0')
+        
+        # Stampa il numero di zeri per la riga corrente
+        print(f"Riga {line_num}: {zero_count} zeri")
+
diff --git a/src/DetectorConstruction.cc b/src/DetectorConstruction.cc
index b490a5262764a372216908abe9e8dc678ea0a5c0..7303de24a7e22ff7bea2c10ce5df63ef380839c6 100644
--- a/src/DetectorConstruction.cc
+++ b/src/DetectorConstruction.cc
@@ -39,6 +39,7 @@
 
 #include "G4GDMLParser.hh"
 
+#include <iostream>
 #include <fstream>
 #include <vector>
 #include <string>
@@ -241,15 +242,15 @@ void DetectorConstruction::DefineMaterials()
 	G4Element*  Cu = new G4Element("Copper"    , "Cu", z = 29., a =  63.55*g/mole);
     G4Element*  Ge = new G4Element("Germanium"   , "Ge", z = 32., a =  72.63*g/mole);
     // G4Element*  As = new G4Element("Arsenic"   , "As", z = 33., a =  74.92*g/mole);
-	 G4Element*  Br = new G4Element("Bromine"   , "Br", z = 35., a =  79.90*g/mole);
+	G4Element*  Br = new G4Element("Bromine"   , "Br", z = 35., a =  79.90*g/mole);
     // G4Element*  Mo = new G4Element("Molybdenum", "Mo", z = 42., a =  95.94*g/mole);
     G4Element*  I  = new G4Element("Iodine"    , "I" , z = 53., a = 126.90*g/mole);
     G4Element*  Cs = new G4Element("Caesium"   , "Cs", z = 55., a = 132.90*g/mole);
     G4Element*  La = new G4Element("Lanthanium", "La", z = 57., a = 138.90*g/mole);
     // G4Element*  Ta = new G4Element("Tantalum"  , "Ta", z = 73., a = 180.94*g/mole);
-     G4Element*  W  = new G4Element("Tungsten"  , "W" , z = 74., a = 183.84*g/mole);
+    G4Element*  W  = new G4Element("Tungsten"  , "W" , z = 74., a = 183.84*g/mole);
     // G4Element*  Pb = new G4Element("Lead"      , "Pb", z = 82., a = 207.20*g/mole);
-     G4Element*  Bi = new G4Element("Bismuth"   , "Bi", z = 83., a = 208.98*g/mole);
+    G4Element*  Bi = new G4Element("Bismuth"   , "Bi", z = 83., a = 208.98*g/mole);
 
 	// Materials 
 	// Vacuum
@@ -310,26 +311,26 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
 	G4SolidStore::GetInstance()->Clean();
 
 
-	// *** Experimental hall (world volume) ***
+	// ! Experimental hall (world volume)
     
 	// Solid
 	G4Box* experimentalHall_box = new G4Box("experimentalHall_box",
-									  		worldSide/2., worldSide/2., worldSide/2.);
+									worldSide/2., worldSide/2., worldSide/2.);
 	// Logical
 	experimentalHall_log  = new G4LogicalVolume(experimentalHall_box,
-	                                            defaultMaterial, "experimentalHall_log", 0, 0, 0);
+                                            defaultMaterial, "experimentalHall_log", 0, 0, 0);
 	// Physical
 	experimentalHall_phys = new G4PVPlacement(0,
-											  G4ThreeVector(0,0,0),
-											  experimentalHall_log,
-											  "experimentalHall_phys",
-											  0,
-											  false,
-											  0);
+											G4ThreeVector(0,0,0),
+											experimentalHall_log,
+											"experimentalHall_phys",
+											0,
+											false,
+											0);
 
     
     
-    // *** Scintillator ***
+    // ! Scintillator
     
     // Module parameterisation
     G4int numberOfBars = n_side*n_side;
@@ -340,9 +341,9 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double scint_container_side_y = (scint_y + scint_gap)*n_side;
     G4double scint_container_side_z = scint_z;
     G4Box* scint_container_box = new G4Box("scint_container_box",
-                                           scint_container_side_x/2., scint_container_side_y/2., scint_container_side_z/2.);
+                                            scint_container_side_x/2., scint_container_side_y/2., scint_container_side_z/2.);
     G4LogicalVolume* scint_container_log = new G4LogicalVolume(scint_container_box,
-                                                               defaultMaterial, "scint_container_log", 0, 0, 0);
+                                                                defaultMaterial, "scint_container_log", 0, 0, 0);
     G4VPhysicalVolume* scint_container_phys = new G4PVPlacement(0,
                                                                 G4ThreeVector(0.,0.,-scint_z/2.),
                                                                 scint_container_log,
@@ -368,7 +369,7 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     
 									
 									
-    // *** Side Collimator ***
+    // ! Side Collimator
     
     G4double coll_side_x = scint_container_side_x;
     G4double coll_side_y = scint_container_side_y;
@@ -382,12 +383,12 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double coll_displacement_y = 0;
     G4double coll_displacement_z = -scint_z + coll_side_height/2.;
     coll_sideXp_phys = new G4PVPlacement(0,
-                                         G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
-                                         coll_sideXp_log,
-                                         "coll_sideXp_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
+                                        coll_sideXp_log,
+                                        "coll_sideXp_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     // Solid
     G4Box* coll_sideXm_box = new G4Box("coll_sideXm_box", coll_side_thick/2., coll_side_x/2., coll_side_height/2.);
@@ -398,12 +399,12 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     coll_displacement_y = 0.;
     coll_displacement_z = -scint_z + coll_side_height/2.;
     coll_sideXm_phys = new G4PVPlacement(0,
-                                         G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
-                                         coll_sideXm_log,
-                                         "coll_sideXm_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
+                                        coll_sideXm_log,
+                                        "coll_sideXm_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     
     // Solid
@@ -415,12 +416,12 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     coll_displacement_y = (coll_side_y/2. + coll_side_thick/2.);
     coll_displacement_z = -scint_z + coll_side_height/2.;
     coll_sideYp_phys = new G4PVPlacement(0,
-                                         G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
-                                         coll_sideYp_log,
-                                         "coll_sideYp_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
+                                        coll_sideYp_log,
+                                        "coll_sideYp_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     // Solid
     G4Box* coll_sideYm_box = new G4Box("coll_sideYm_box", coll_side_y/2.+coll_side_thick, coll_side_thick/2., coll_side_height/2.);
@@ -431,20 +432,20 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     coll_displacement_y = -(coll_side_y/2. + coll_side_thick/2.);
     coll_displacement_z = -scint_z + coll_side_height/2.;
     coll_sideYm_phys = new G4PVPlacement(0,
-                                         G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
-                                         coll_sideYm_log,
-                                         "coll_sideYm_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
+                                        coll_sideYm_log,
+                                        "coll_sideYm_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     
-    // *** Spacecraft bus (box approximation) ***
+    // ! Spacecraft bus (box approximation)
     // TODO: insert here new S/C model (hexagonal, rotated wrt XGIS unit)
     
     // Solid
     G4Box* bus1_box = new G4Box("bus1_box",
-                                       (coll_side_x + 2*coll_side_thick)/2., (coll_side_y + 2*coll_side_thick)/2., bus_thick/2.);
+                                        (coll_side_x + 2*coll_side_thick)/2., (coll_side_y + 2*coll_side_thick)/2., bus_thick/2.);
     // Logical
     bus1_log = new G4LogicalVolume(bus1_box, busMaterial, "bus1_log", 0, 0, 0);
     // Physical
@@ -452,12 +453,12 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     coll_displacement_y = 0;
     coll_displacement_z = -scint_z - optCoupler_thick - sdd_thick  - bus_thick/2.;
     bus1_phys = new G4PVPlacement(0,
-                                   G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
-                                   bus1_log,
-                                   "bus1_phys",
-                                   experimentalHall_log,
-                                   false,
-                                   0);
+                                    G4ThreeVector(coll_displacement_x,coll_displacement_y,coll_displacement_z),
+                                    bus1_log,
+                                    "bus1_phys",
+                                    experimentalHall_log,
+                                    false,
+                                    0);
 
 //    // Solid
 //    G4Box* bus1_box = new G4Box("bus1_box",
@@ -478,7 +479,7 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
 //                                  0);
 
     
-    // *** SDDs ***
+    // ! SDDs
     
     // Solid
     G4Box* sdd_box = new G4Box("sdd_box", coll_side_x/2., coll_side_y/2., sdd_thick/2.);
@@ -491,26 +492,26 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double sddUpper_y = 0;
     G4double sddUpper_z = sdd_thick/2. + optCoupler_thick;
     sddUpper_phys = new G4PVPlacement(0,
-                                         G4ThreeVector(sddUpper_x,sddUpper_y,sddUpper_z),
-                                         sddUpper_log,
-                                         "sddUpper_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4ThreeVector(sddUpper_x,sddUpper_y,sddUpper_z),
+                                        sddUpper_log,
+                                        "sddUpper_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
 
     G4double sddLower_x = 0;
     G4double sddLower_y = 0;
     G4double sddLower_z = -scint_z - sdd_thick/2.;
     sddLower_phys = new G4PVPlacement(0,
-                                      G4ThreeVector(sddLower_x,sddLower_y,sddLower_z),
-                                      sddLower_log,
-                                      "sddLower_phys",
-                                      experimentalHall_log,
-                                      false,
-                                      0);
+                                        G4ThreeVector(sddLower_x,sddLower_y,sddLower_z),
+                                        sddLower_log,
+                                        "sddLower_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     
-    // *** Optical coupler ***
+    // ! Optical coupler
     
     // Solid
     G4Box* optCoupler_box = new G4Box("sdd_box", coll_side_x/2., coll_side_y/2., sdd_thick/2.);
@@ -522,54 +523,89 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double optCoupler_y = 0;
     G4double optCoupler_z = optCoupler_thick/2.;
     optCoupler_phys = new G4PVPlacement(0,
-                                      G4ThreeVector(optCoupler_x,optCoupler_y,optCoupler_z),
-                                      optCoupler_log,
-                                      "optCoupler_phys",
-                                      experimentalHall_log,
-                                      false,
-                                      0);
+                                        G4ThreeVector(optCoupler_x,optCoupler_y,optCoupler_z),
+                                        optCoupler_log,
+                                        "optCoupler_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
 
 
     
-    // *** Mask ***
+    // ! Mask
+
     // Solid
     G4Box* mask_container_box = new G4Box("mask_box", mask_side_x/2., mask_side_y/2., mask_thick/2.);
+
     // Logical
     G4LogicalVolume* mask_container_log = new G4LogicalVolume(mask_container_box, defaultMaterial, "mask_container_log", 0, 0, 0);
     
     // Physical
     G4VPhysicalVolume* mask_container_phys = new G4PVPlacement(0,
-                                                                  G4ThreeVector(0,0,mask_focalDistance+sdd_thick+optCoupler_thick),
-                                                                  mask_container_log,
-                                                                  "mask_container_phys",
-                                                                  experimentalHall_log,
-                                                                  false,
-                                                                  0);
+                                                                G4ThreeVector(0,0,mask_focalDistance+sdd_thick+optCoupler_thick),
+                                                                mask_container_log,
+                                                                "mask_container_phys",
+                                                                experimentalHall_log,
+                                                                false,
+                                                                0);
     
 
-    G4double mask_elem_side_x = mask_side_x/(2*n_mask_elem_side);
-    G4double mask_elem_side_y = mask_side_y/(2*n_mask_elem_side);
-
-    G4int n_mask_elem_replicas = (2*n_mask_elem_side) * (2*n_mask_elem_side) * 1/2;
+    // G4double mask_elem_side_x = mask_side_x/(2*n_mask_elem_side);
+    // G4double mask_elem_side_y = mask_side_y/(2*n_mask_elem_side);
+    // G4int n_mask_elem_replicas = (2*n_mask_elem_side) * (2*n_mask_elem_side) * 1/2;
+    
+    G4double mask_elem_side_x = 1.027*cm;
+    G4double mask_elem_side_y = 1.027*cm;
+    //G4double mask_elem_side_x = (mask_side_x/n_mask_elem_side)*cm;
+    //G4double mask_elem_side_y = (mask_side_y/n_mask_elem_side)*cm;
+    G4double gap = (mask_side_x/n_mask_elem_side) - mask_elem_side_x;
     
     // Solid
     G4Box* mask_box = new G4Box("mask_box", mask_elem_side_x/2., mask_elem_side_y/2., mask_thick/2.);
+
     // Logical
     mask_log = new G4LogicalVolume(mask_box, maskMaterial, "mask_log", 0, 0, 0);
+
+    // Creazione dell'array per le posizioni degli zeri
+    std::vector<std::pair<int, int>> zeroPositions;
+
     // Physical
-    maskParam = new MaskParameterisation(mask_elem_side_x, mask_elem_side_y, n_mask_elem_side);
+    MaskParameterisation* maskParam = new MaskParameterisation(mask_elem_side_x, mask_elem_side_y, n_mask_elem_side, gap, "mask.dat");
+
+    int totalZeros = maskParam->GetTotalZeros();
+    
+    if (totalZeros != -1) {
+        // for (const auto& pos : zeroPositions) {
+        //     G4cout << "Zero a posizione: (" << pos.first << ", " << pos.second << ")" << G4endl;
+        // }
+        // G4cout << "Numero totale di zeri: " << totalZeros << G4endl;
+        // G4cout << "gap: " << gap << G4endl;
+
+        // Posizionamento parametrizzato delle repliche
+        mask_phys = new G4PVParameterised(
+                                        "mask_phys",            // Nome
+                                        mask_log,               // Logica dell'elemento maschera
+                                        mask_container_log,     // Volume madre
+                                        kXAxis,                 // Asse lungo cui avviene il posizionamento
+                                        totalZeros,             // Numero di repliche
+                                        maskParam               // Parametrizzazione
+            );
+    } else {
+        G4cerr << "Errore durante il caricamento del file mask.dat." << G4endl;
+    }
+
     
-    mask_phys = new G4PVParameterised("mask_phys",           // their name
-                                       mask_log,                // their logical volume
-                                       mask_container_log,  // Mother logical volume
-                                       kXAxis,                  // Are placed along this axis
-                                       n_mask_elem_replicas,      // Number of replicas
-                                       maskParam);           // The parametrisation
+    // mask_phys = new G4PVParameterised("mask_phys",           // their name
+    //                                    mask_log,                // their logical volume
+    //                                    mask_container_log,  // Mother logical volume
+    //                                    kXAxis,                  // Are placed along this axis
+    //                                    n_mask_elem_replicas,      // Number of replicas
+    //                                    maskParam);           // The parametrisation
 
     
     
-    // *** Upper Collimator, internal ***
+    // ! Upper Collimator, internal
     
     // Slabs with trapezoidal shape, around the SDD
     // Remember the calling sequence for the G4Trap class:
@@ -593,14 +629,14 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double base_side_x = coll_side_x + 2*coll_side_thick;
     G4double base_side_y = coll_side_y + 2*coll_side_thick;
 
-    G4cout << "base_side_x, base_side_y (cm) " << base_side_x/cm << " " << base_side_y/cm << G4endl;
+    //G4cout << "base_side_x, base_side_y (cm) " << base_side_x/cm << " " << base_side_y/cm << G4endl;
 
     // Rotation angles for the y-side and x-side collimators (i.e. inclination)
     double xrotTheta = atan((mask_side_x + coll_upper1_thick/2 - base_side_x)/(2*mask_focalDistance));
     double yrotTheta = atan((mask_side_y + coll_upper1_thick/2 - base_side_y)/(2*mask_focalDistance));
 
-    G4cout << "xrotTheta, yrotTheta (rad) " << xrotTheta << " " << yrotTheta << G4endl;
-    G4cout << "xrotTheta, yrotTheta (deg) " << 180/3.141592*(xrotTheta) << " " << 180/3.141592*(yrotTheta) << G4endl;
+    //G4cout << "xrotTheta, yrotTheta (rad) " << xrotTheta << " " << yrotTheta << G4endl;
+    //G4cout << "xrotTheta, yrotTheta (deg) " << 180/3.141592*(xrotTheta) << " " << 180/3.141592*(yrotTheta) << G4endl;
 
     // Solid (for yPlus, yMinus)
     G4double   pDzY   = mask_focalDistance/cos(yrotTheta)/2. ;              // half-height
@@ -611,7 +647,7 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double   pDx3   = (base_side_x + (mask_side_x - base_side_x))/2.;     // mask side
     G4double   pDx4   = pDx3; 						                        // the other side of the upper face is the same
     G4Trap* coll_upper1_trap_y = new G4Trap("coll_upper1_trap_y",
-                                          pDzY, 0, 0, pDy1, pDx1, pDx2, 0, pDy2, pDx3, pDx4, 0);
+                                        pDzY, 0, 0, pDy1, pDx1, pDx2, 0, pDy2, pDx3, pDx4, 0);
     
     // Solid (for xPlus, xMinus)
     G4double pDzX    = mask_focalDistance/cos(xrotTheta)/2. ;               // half-height
@@ -620,17 +656,17 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     pDx3   = (base_side_y  + (mask_side_y - base_side_y))/2.;      		    // mask side
     pDx4   = pDx3;
     G4Trap* coll_upper1_trap_x = new G4Trap("coll_upper1_trap_x",
-                                          pDzX, 0, 0, pDy1, pDx1, pDx2, 0, pDy2, pDx3, pDx4, 0);
+                                        pDzX, 0, 0, pDy1, pDx1, pDx2, 0, pDy2, pDx3, pDx4, 0);
     
     // Logical
     coll_upper1Yp_log = new G4LogicalVolume(coll_upper1_trap_y,
-                                          collUpper1Material, "coll_upper1Yp_log", 0, 0, 0);
+                                        collUpper1Material, "coll_upper1Yp_log", 0, 0, 0);
     coll_upper1Ym_log = new G4LogicalVolume(coll_upper1_trap_y,
-                                          collUpper1Material, "coll_upper1Ym_log", 0, 0, 0);
+                                        collUpper1Material, "coll_upper1Ym_log", 0, 0, 0);
     coll_upper1Xp_log = new G4LogicalVolume(coll_upper1_trap_x,
-                                          collUpper1Material, "coll_upper1Xp_log", 0, 0, 0);
+                                        collUpper1Material, "coll_upper1Xp_log", 0, 0, 0);
     coll_upper1Xm_log = new G4LogicalVolume(coll_upper1_trap_x,
-                                          collUpper1Material, "coll_upper1Xm_log", 0, 0, 0);
+                                        collUpper1Material, "coll_upper1Xm_log", 0, 0, 0);
     
     // Physical
     // yPlus collimator
@@ -638,24 +674,24 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     yRotPlus->rotateX(-yrotTheta);
     G4ThreeVector yShiftPlus(0, base_side_y/2.+ coll_upper1_thick/2. + pDzY*sin(yrotTheta), pDzY*cos(yrotTheta));
     coll_upper1Yp_phys = new G4PVPlacement(
-                                         G4Transform3D(*yRotPlus, yShiftPlus),
-                                         coll_upper1Yp_log,
-                                         "collUpper1Yp_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4Transform3D(*yRotPlus, yShiftPlus),
+                                        coll_upper1Yp_log,
+                                        "collUpper1Yp_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     // yMinus collimator
     G4RotationMatrix* yRotMinus = new G4RotationMatrix;
     yRotMinus->rotateX(yrotTheta);
     G4ThreeVector yShiftMinus(0, -(base_side_y/2.+ coll_upper1_thick/2. + pDzY*sin(yrotTheta)), pDzY*cos(yrotTheta));
     coll_upper1Ym_phys = new G4PVPlacement(
-                                         G4Transform3D(*yRotMinus, yShiftMinus),
-                                         coll_upper1Ym_log,
-                                         "collUpper1Ym_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4Transform3D(*yRotMinus, yShiftMinus),
+                                        coll_upper1Ym_log,
+                                        "collUpper1Ym_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
     
     // xPlus collimator
     G4RotationMatrix* xRotPlus = new G4RotationMatrix;
@@ -663,12 +699,12 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     xRotPlus->rotateY(xrotTheta);
     G4ThreeVector xShiftPlus(base_side_x/2.+ coll_upper1_thick/2. + pDzX*sin(xrotTheta), 0, pDzX*cos(xrotTheta));
     coll_upper1Xp_phys = new G4PVPlacement(
-                                         G4Transform3D(*xRotPlus, xShiftPlus),
-                                         coll_upper1Xp_log,
-                                         "collUpper1Xp_phys",
-                                         experimentalHall_log,
-                                         false,
-                                         0);
+                                        G4Transform3D(*xRotPlus, xShiftPlus),
+                                        coll_upper1Xp_log,
+                                        "collUpper1Xp_phys",
+                                        experimentalHall_log,
+                                        false,
+                                        0);
 
     // xMinus collimator
     G4RotationMatrix* xRotMinus = new G4RotationMatrix;
@@ -676,15 +712,15 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     xRotMinus->rotateY(-xrotTheta);
     G4ThreeVector xShiftMinus(-(base_side_x/2.+ coll_upper1_thick/2. + pDzX*sin(xrotTheta)), 0, pDzX*cos(xrotTheta));
     coll_upper1Xm_phys = new G4PVPlacement(
-                                         G4Transform3D(*xRotMinus, xShiftMinus),
-                                         coll_upper1Xm_log,
-                                         "collUpper1Xm_phys",
-                                         experimentalHall_log, 
-                                         false, 
-                                         0);
+                                        G4Transform3D(*xRotMinus, xShiftMinus),
+                                        coll_upper1Xm_log,
+                                        "collUpper1Xm_phys",
+                                        experimentalHall_log, 
+                                        false, 
+                                        0);
     
     
-    // *** Upper Collimator, external ***
+    // ! Upper Collimator, external
     
     // Slabs with trapezoidal shape, around the SDD
     // Remember the calling sequence for the G4Trap class:
@@ -721,7 +757,7 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     G4double   p2Dx3   = (base_side_x + (scaled_mask_side_x - base_side_x))/2.;     // mask side
     G4double   p2Dx4   = p2Dx3;                                                 // the other side of the upper face is the same
     G4Trap* coll_upper2_trap_y = new G4Trap("coll_upper2_trap_y",
-                                           p2DzY, 0, 0, p2Dy1, p2Dx1, p2Dx2, 0, p2Dy2, p2Dx3, p2Dx4, 0);
+                                        p2DzY, 0, 0, p2Dy1, p2Dx1, p2Dx2, 0, p2Dy2, p2Dx3, p2Dx4, 0);
     
     // Solid (for xPlus, xMinus)
     G4double p2DzX    = coll_upper2_height/cos(xrotTheta)/2. ;               // half-height
@@ -730,7 +766,7 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     p2Dx3   = (base_side_y  + (scaled_mask_side_y - base_side_y))/2.;                  // mask side
     p2Dx4   = p2Dx3;
     G4Trap* coll_upper2_trap_x = new G4Trap("coll_upper2_trap_x",
-                                           p2DzX, 0, 0, p2Dy1, p2Dx1, p2Dx2, 0, p2Dy2, p2Dx3, p2Dx4, 0);
+                                        p2DzX, 0, 0, p2Dy1, p2Dx1, p2Dx2, 0, p2Dy2, p2Dx3, p2Dx4, 0);
     
     // Logical
     coll_upper2Yp_log = new G4LogicalVolume(coll_upper2_trap_y,
@@ -746,42 +782,42 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
     // yPlus collimator
     G4ThreeVector yShiftPlus2(0, base_side_y/2.+ coll_upper1_thick/cos(yrotTheta) + coll_upper2_thick/2. + p2DzY*sin(yrotTheta), p2DzY*cos(yrotTheta));
     coll_upper2Yp_phys = new G4PVPlacement(
-                                           G4Transform3D(*yRotPlus, yShiftPlus2),
-                                           coll_upper2Yp_log,
-                                           "collUpper2Yp_phys",
-                                           experimentalHall_log,
-                                           false,
-                                           0);
+                                            G4Transform3D(*yRotPlus, yShiftPlus2),
+                                            coll_upper2Yp_log,
+                                            "collUpper2Yp_phys",
+                                            experimentalHall_log,
+                                            false,
+                                            0);
     
     // yMinus collimator
     G4ThreeVector yShiftMinus2(0, -(base_side_y/2.+ coll_upper1_thick/cos(yrotTheta) + coll_upper2_thick/2. + p2DzY*sin(yrotTheta)), p2DzY*cos(yrotTheta));
     coll_upper2Ym_phys = new G4PVPlacement(
-                                           G4Transform3D(*yRotMinus, yShiftMinus2),
-                                           coll_upper2Ym_log,
-                                           "collUpper2Ym_phys",
-                                           experimentalHall_log,
-                                           false,
-                                           0);
+                                            G4Transform3D(*yRotMinus, yShiftMinus2),
+                                            coll_upper2Ym_log,
+                                            "collUpper2Ym_phys",
+                                            experimentalHall_log,
+                                            false,
+                                            0);
     
     // xPlus collimator
     G4ThreeVector xShiftPlus2(base_side_x/2.+ coll_upper1_thick/cos(xrotTheta) + coll_upper2_thick/2. + p2DzX*sin(xrotTheta), 0, p2DzX*cos(xrotTheta));
     coll_upper2Xp_phys = new G4PVPlacement(
-                                           G4Transform3D(*xRotPlus, xShiftPlus2),
-                                           coll_upper2Xp_log,
-                                           "collUpper2Xp_phys",
-                                           experimentalHall_log,
-                                           false,
-                                           0);
+                                            G4Transform3D(*xRotPlus, xShiftPlus2),
+                                            coll_upper2Xp_log,
+                                            "collUpper2Xp_phys",
+                                            experimentalHall_log,
+                                            false,
+                                            0);
     
     // xMinus collimator
     G4ThreeVector xShiftMinus2(-(base_side_x/2.+ coll_upper1_thick/cos(xrotTheta) + coll_upper2_thick/2. + p2DzX*sin(xrotTheta)), 0, p2DzX*cos(xrotTheta));
     coll_upper2Xm_phys = new G4PVPlacement(
-                                           G4Transform3D(*xRotMinus, xShiftMinus2),
-                                           coll_upper2Xm_log,
-                                           "collUpper2Xm_phys",
-                                           experimentalHall_log,
-                                           false,
-                                           0);
+                                            G4Transform3D(*xRotMinus, xShiftMinus2),
+                                            coll_upper2Xm_log,
+                                            "collUpper2Xm_phys",
+                                            experimentalHall_log,
+                                            false,
+                                            0);
     
     
     
@@ -844,14 +880,15 @@ G4VPhysicalVolume* DetectorConstruction::Construct()
 	// Dump the geometry in a GDML file, solo se non esiste
 	G4String fWriteFile = "geometry.gdml";
 
-    std::ifstream fileCheck(fWriteFile.c_str());
-    if (fileCheck.good()) {
-        std::cout << "il file geometry.gdml esiste già" << std::endl;
-    } else {
-        G4GDMLParser parser;
-	    //std::remove(fWriteFile.c_str());
-	    parser.Write(fWriteFile, experimentalHall_phys, false);
-    }
+    // questo pezzo non va bene perche se modifico non me lo sovrascrivr //! MIGLIORARE
+    // std::ifstream fileCheck(fWriteFile.c_str());
+    // if (fileCheck.good()) {
+    //     G4cout << "il file geometry.gdml esiste già" << G4endl;
+    // } else {
+    //     G4GDMLParser parser;
+	//     //std::remove(fWriteFile.c_str());
+	//     parser.Write(fWriteFile, experimentalHall_phys, false);
+    // }
 
 	// The function must return the physical volume of the world
 	return experimentalHall_phys;
@@ -873,9 +910,9 @@ void DetectorConstruction::ConstructSDandField()
 
     // Instantiation of the sensitive detector and readout geometry
     SensitiveDetector* scint_SD  = new SensitiveDetector("SCI",
-                                         n_side,
-                                         scint_x+scint_gap, scint_z,
-                                         NbOfSlicesPerBar);
+                                        n_side,
+                                        scint_x+scint_gap, scint_z,
+                                        NbOfSlicesPerBar);
     
     
     sdman->AddNewDetector(scint_SD); // Mandatory since Geant v. 4.10.03
@@ -883,8 +920,8 @@ void DetectorConstruction::ConstructSDandField()
     
     // Instantiation of the sensitive detector and readout geometry
     SDDSensitiveDetector* sdd_SD  = new SDDSensitiveDetector("SDD",
-                                                          scint_x+scint_gap,
-                                                          n_side, n_side);
+                                                            scint_x+scint_gap,
+                                                            n_side, n_side);
     sdman->AddNewDetector(sdd_SD); // Mandatory since Geant v. 4.10.03
     SetSensitiveDetector(sddUpper_log, sdd_SD);
 }
@@ -947,6 +984,9 @@ void DetectorConstruction::PrintParameters()
 			<< "\n Scint Side X                     (cm) : " 	<< scint_x/cm
 			<< "\n Scint Side Y                     (cm) : " 	<< scint_y/cm
 			<< "\n Scint Side Z                     (cm) : " 	<< scint_z/cm
+            << "\n mask_side_x                      (cm) : "    << mask_side_x/cm
+            << "\n mask_side_y                      (cm) : "    << mask_side_y/cm
+            << "\n n_mask_elem_side                      : "    << n_mask_elem_side
             << "\n Scint material                        : " 	<< scintMaterial -> GetName()
             << "\n Mask material                         : "    << maskMaterial -> GetName()
             << "\n Collimator 1 material                 : "    << collUpper1Material -> GetName()
diff --git a/src/MaskParameterisation.cc b/src/MaskParameterisation.cc
index 0009ab80ba0850f3e811e02779329392c4977603..38f85a220f0a2486a15ce019e2ac34d67bf00b78 100644
--- a/src/MaskParameterisation.cc
+++ b/src/MaskParameterisation.cc
@@ -7,12 +7,21 @@
 #include "G4RotationMatrix.hh"
 #include "G4Box.hh"
 
+#include <iostream>
+#include <fstream>
+#include <string>
+#include <sstream>
+#include <vector>
 
-MaskParameterisation::MaskParameterisation(G4double side_length_X, G4double side_length_Y, G4int n_side)
+
+MaskParameterisation::MaskParameterisation(G4double side_length_X, G4double side_length_Y, G4int n_side, G4double gap, const std::string& filename)
+    : fSideX(side_length_X), fSideY(side_length_Y), nSide(n_side), fGap(gap) 
 {
-    fSideX    =  side_length_X;
-    fSideY    =  side_length_Y;
-    nSide    =  n_side;
+    // Carica zeroPositions dal file
+    int totalZeros = LoadZeroPositions(filename);
+    if (totalZeros == -1) {
+        G4cerr << "Errore durante il caricamento del file " << filename << G4endl;
+    }
 }
 
 
@@ -20,26 +29,89 @@ MaskParameterisation::~MaskParameterisation()
 {;}
 
 
+int MaskParameterisation::LoadZeroPositions(const std::string& filename)
+{
+    std::ifstream infile(filename);  //apre il file in modalità lettura
+    if (!infile) {
+        std::cerr << "Errore nell'apertura del file " << filename << std::endl;
+        return -1;
+    }
+
+    std::string line; //memorizza la riga corrente del file
+    int rowID = 0;
+    int totalZeros = 0;
+
+    // Leggi il file riga per riga
+    while (std::getline(infile, line)) { // legge il file una riga alla volta. std::getline carica il contenuto della riga corrente in line
+        // Salta le righe commentate
+        if (line[0] == '#') continue;
+
+        std::istringstream iss(line);  // crea uno stream di input (iss) dalla riga letta (line), per processare ogni elemento della riga come valore numerico
+        int colID = 0;
+        int value;   // value memorizza ciascun numero estratto dalla riga.
+
+        // Leggi ogni numero della riga e controlla se è uno zero
+        while (iss >> value) {  // >> estrae il prossimo elemento dallo stream iss e lo assegna a value.
+            if (value == 0) {  // Se l'operazione ha successo (ossia se iss ha ancora un numero da leggere), il ciclo while continua; altrimenti, iss >> value restituisce false, terminando il ciclo while
+                // Aggiungi la posizione (rowID, colID) all'array zeroPositions
+                zeroPositions.push_back(std::make_pair(rowID, colID));
+                totalZeros++;
+            }
+            colID++;
+        }
+        rowID++;
+    }
+
+    infile.close();
+    return totalZeros;
+}
+
+int MaskParameterisation::GetTotalZeros() const 
+{
+    return zeroPositions.size();  // Ritorna il numero totale di zeri, che corrisponde alla dimensione del vettore zeroPositions
+}
+
+
 void MaskParameterisation::ComputeTransformation (const G4int copyNo, G4VPhysicalVolume* physVol) const
 {
     G4double xCell = 0.*cm;
     G4double yCell = 0.*cm;
     G4double zCell = 0.*cm;
 
-    if (nSide % 2 == 0) // Even number of tiles per side
-    {
-        G4int rowID = copyNo / nSide;                                   // identifies the row of the tile
-        G4int colID = (copyNo % nSide)*2 + (((int) copyNo/nSide)%2);    // in order to have tiles in odd-numbered rows shifted by one column w.r.t. the adjacent rows
-//        G4cout << "*** DEBUG copyNo " << copyNo << " rowID " << rowID << " colID " << colID << G4endl;
-        xCell = (2*colID - (2*nSide -1)) *fSideX/2;
-        yCell = (2*rowID - (2*nSide -1)) *fSideY/2;
-//        G4cout << "*** DEBUG xCell " << xCell/cm << " yCell " << yCell/cm << G4endl;
-//        G4cout << " " << G4endl;
-    }
-        
-    physVol->SetTranslation(G4ThreeVector(xCell, yCell, zCell));
+    int rowID = zeroPositions[copyNo].first;
+    int colID = zeroPositions[copyNo].second;
+
+    xCell = (fSideX) *((-nSide+1)/2 + colID);  // potrei scrivere fSideX+fGap se voglio aggiungere il gap
+    yCell = (fSideY) *((-nSide+1)/2 + rowID); 
+
+    physVol->SetTranslation(G4ThreeVector(xCell, yCell, zCell)); 
+
+    // G4cout << "*** DEBUG copyNo " << copyNo << " rowID " << rowID << " colID " << colID << G4endl;
+    // G4cout << "*** DEBUG xCell " << xCell/cm << " yCell " << yCell/cm << G4endl;    
     
 }
 
 
 
+
+// ! OLD MASK
+// void MaskParameterisation::ComputeTransformation (const G4int copyNo, G4VPhysicalVolume* physVol) const
+// {
+//     G4double xCell = 0.*cm;
+//     G4double yCell = 0.*cm;
+//     G4double zCell = 0.*cm;
+
+//     if (nSide % 2 == 0) // Even number of tiles per side
+//     {
+//         G4int rowID = copyNo / nSide;                                   // identifies the row of the tile
+//         G4int colID = (copyNo % nSide)*2 + (((int) copyNo/nSide)%2);    // in order to have tiles in odd-numbered rows shifted by one column w.r.t. the adjacent rows
+// //        G4cout << "*** DEBUG copyNo " << copyNo << " rowID " << rowID << " colID " << colID << G4endl;
+//         xCell = (2*colID - (2*nSide -1)) *fSideX/2;
+//         yCell = (2*rowID - (2*nSide -1)) *fSideY/2;
+// //        G4cout << "*** DEBUG xCell " << xCell/cm << " yCell " << yCell/cm << G4endl;
+// //        G4cout << " " << G4endl;
+//     }
+    
+//     physVol->SetTranslation(G4ThreeVector(xCell, yCell, zCell));
+    
+// }
diff --git a/xgis_M7 b/xgis_M7
index c03587f07ce55c209a5acd883d4afa7742510003..7c7706bbcc79ec7141751625e5ddc9cc7d80623c 100755
Binary files a/xgis_M7 and b/xgis_M7 differ