Skip to content

Référence API

Remarque (Éléments privés)

Ce module contient des classes et fonctions « privées » dont le nom commence par un trait de soulignement. Par défaut, leurs détails ne sont pas inclus dans la documentation.

Package complet

Package de lecture ISD

Ce package analyse le fichier Description.xml du dossier ISD et rend les données binaires de l'image correspondante accessibles sous forme de tableau NumPy 2D avec le type approprié (uint8/16/32).

Ce package inclut
  • IsdReader : le point d'entrée principal pour la lecture des jeux de données ISD, c'est-à-dire une classe d'objet qui englobe les données ISD elles-mêmes.
  • Des classes de gestion des exceptions pour diverses erreurs.

Exemple d'utilisation :

from isdreader import IsdReader isd = IsdReader(isd_path="/path/to/folder.isd") ch = isd.GetCh(1) dg = ch.GetDataGate(2) img = dg.GetImage("AP") arr = img.load_image() Ici, arr est un tableau NumPy 2D.

BinaryFileNotFound

Bases: Exception

Une exception se produit si le fichier binaire spécifié est introuvable dans le dossier ISD.

Source code in .build\fr\isdreader\isd_helper.py
55
56
57
58
59
class BinaryFileNotFound(Exception):
    """
    Une exception se produit si le fichier binaire spécifié est introuvable dans le dossier ISD.
    """
    pass

DescriptionNotFound

Bases: Exception

Une exception se produit si le fichier Description.xml est introuvable dans le dossier ISD.

Source code in .build\fr\isdreader\isd_helper.py
41
42
43
44
45
class DescriptionNotFound(Exception):
    """
    Une exception se produit si le fichier Description.xml est introuvable dans le dossier ISD.
    """
    pass

InvalidChannel

Bases: Exception

Une exception se produit lorsque l'index du canal spécifié est invalide.

Source code in .build\fr\isdreader\isd_helper.py
13
14
15
16
17
class InvalidChannel(Exception):
    """
    Une exception se produit lorsque l'index du canal spécifié est invalide.
    """
    pass

InvalidDataGate

Bases: Exception

Une exception se produit lorsque l'index de la porte de données spécifié est invalide.

Source code in .build\fr\isdreader\isd_helper.py
20
21
22
23
24
class InvalidDataGate(Exception):
    """
    Une exception se produit lorsque l'index de la porte de données spécifié est invalide.
    """
    pass

IsdNotFound

Bases: Exception

Une exception se produit lorsque le dossier ISD spécifié n'existe pas.

Source code in .build\fr\isdreader\isd_helper.py
34
35
36
37
38
class IsdNotFound(Exception):
    """
    Une exception se produit lorsque le dossier ISD spécifié n'existe pas.
    """
    pass

IsdReader

Classe racine représentant l'intégralité du dossier ISD Cette classe est le point d'entrée principal pour accéder à tous les canaux, DataGate et images du jeu de données d'acquisition ISD. Autrement dit, il s'agit d'une classe d'objet englobant l'ensemble des données ISD. Attributs : chemin : Chemin d'accès au dossier ISD à inclure chemin_description : Chemin d'accès au fichier Description.xml (situé directement à la racine du dossier ISD) enregistreur : Instance de l'enregistreur pour cet objet

Source code in .build\fr\isdreader\isd_root.py
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
class IsdReader:
    """
    Classe racine représentant l'intégralité du dossier ISD
    Cette classe est le point d'entrée principal pour accéder à tous les canaux,
    DataGate et images du jeu de données d'acquisition ISD.
    Autrement dit, il s'agit d'une classe d'objet englobant l'ensemble des données ISD.
    Attributs :
      chemin : Chemin d'accès au dossier ISD à inclure
      chemin_description : Chemin d'accès au fichier Description.xml 
      (situé directement à la racine du dossier ISD)
      enregistreur : Instance de l'enregistreur pour cet objet
    """
# --------------------------------------------------------------------------------------------------------
    def __init__(self, *, isd_path: Union[str, Path], logger: Optional[logging.Logger] = None) -> None:
        """
        Initialise un objet IsdReader à partir du dossier ISD spécifié.
        Arguments :
          isd_path : Chemin d'accès au dossier ISD (chaîne de caractères ou pathlib.Path).
          logger : Instance de journalisation facultative. Journalisation par défaut si None.
        Lève :
          TypeError : Si isd_path n'est ni une chaîne de caractères ni un chemin.
          IsdNotFound : Si le dossier ISD est introuvable.
          DescriptionNotFound : Si le fichier Description.xml est introuvable dans le dossier ISD.
        """
        if not isinstance(isd_path, (str, Path)):
            raise TypeError("isd_path must be str or pathlib.Path")

        self.path = Path(isd_path)
        if not self.path.exists() or not self.path.is_dir():
            raise IsdNotFound(f"ISD folder not found: {isd_path}")

        self.description_path = self.path / "Description.xml"
        if not self.description_path.exists():
            raise DescriptionNotFound(f"Description.xml not found in: {self.path}")

        tree = etree.parse(self.description_path)
        root = tree.getroot()
        isd_root = Path(self.description_path).parent

        self._scan_type = root.findtext("Info/ScanType")
        self._width_pixel = int(root.findtext("Info/WidthPixel") or 0)
        self._height_pixel = int(root.findtext("Info/HeightPixel") or 0)

        wp = root.find("Info/WidthPhysical")
        if wp is not None:
            try:
                self._width_physical = float(wp.text.strip())
            except Exception:
                self._width_physical = None
            self._width_physical_unit = wp.get("Unit")
        else:
            self._width_physical = None
            self._width_physical_unit = None

        hp = root.find("Info/HeightPhysical")
        if hp is not None:
            try:
                self._height_physical = float(hp.text.strip())
            except Exception:
                self._height_physical = None
            self._height_physical_unit = hp.get("Unit")
        else:
            self._height_physical = None
            self._height_physical_unit = None

        self._channels: List[ChChunk] = []
        for ch_elem in root.findall("Channel"):
            self._channels.append(ChChunk(root, ch_elem, isd_root, self._width_pixel or 0, self._height_pixel or 0))

        self._root_elem = root

        self.logger = logger or logging.getLogger(__name__)
# --------------------------------------------------------------------------------------------------------
    def __repr__(self) -> str:
        """
        Cette fonction renvoie un résumé sous forme de chaîne de caractères de l'IsdReader.
        Renvoie :
          Une chaîne de caractères contenant la taille et le nombre de canaux disponibles.
        """
        parts: List[str] = []
        if self._width_pixel is not None and self._height_pixel is not None:
            parts.append(f"size={self._width_pixel}x{self._height_pixel}")
        chs = self.GetCh()
        if chs:
            parts.append(f"channels={','.join(str(int(c)) for c in chs)}")
        return f"IsdReader[{', '.join(parts)}]"
# --------------------------------------------------------------------------------------------------------
    def GetCh(self, ch: Optional[int] = None):
        """
        Récupère une instance de ChChunk ou liste tous les canaux.
        Arguments :
          ch : None ou un numéro de ChChunk spécifié
        Retour :
          Si ch est None, une liste des numéros de canaux disponibles est retournée ;
          sinon, l’instance de ChChunk spécifiée ou None est retournée.
        """
        if ch is None:
            return [c._ch for c in self._channels if c._ch is not None]
        for c in self._channels:
            if c._ch == int(ch):
                return c
        return None
# --------------------------------------------------------------------------------------------------------
    def GetImage(self, *, ch: int, gate: int, image_type: str, slice_no: Optional[int] = 1) -> Optional[ImageChunk]:
        """
        Méthode pour récupérer directement un ImageChunk
        Arguments :
          ch : Numéro du canal (1 origine)
          gate : Numéro du DataGate (1 origine)
          image_type : Type d’image (abrégé, nom complet)
          slice_no : Numéro de la tranche (1 origine, par défaut : 1)
        Retourne :
          Une instance d’ImageChunk correspondant aux critères spécifiés ; sinon, None
        """
        chObj = self.GetCh(ch)
        if chObj is None:
            return None
        gateObj = chObj.GetDataGate(gate)
        if gateObj is None:
            return None
        imgObj = gateObj.GetImage(image_type, slice_no)
        return imgObj

GetCh(ch=None)

Récupère une instance de ChChunk ou liste tous les canaux. Arguments : ch : None ou un numéro de ChChunk spécifié Retour : Si ch est None, une liste des numéros de canaux disponibles est retournée ; sinon, l’instance de ChChunk spécifiée ou None est retournée.

Source code in .build\fr\isdreader\isd_root.py
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
def GetCh(self, ch: Optional[int] = None):
    """
    Récupère une instance de ChChunk ou liste tous les canaux.
    Arguments :
      ch : None ou un numéro de ChChunk spécifié
    Retour :
      Si ch est None, une liste des numéros de canaux disponibles est retournée ;
      sinon, l’instance de ChChunk spécifiée ou None est retournée.
    """
    if ch is None:
        return [c._ch for c in self._channels if c._ch is not None]
    for c in self._channels:
        if c._ch == int(ch):
            return c
    return None

GetImage(*, ch, gate, image_type, slice_no=1)

Méthode pour récupérer directement un ImageChunk Arguments : ch : Numéro du canal (1 origine) gate : Numéro du DataGate (1 origine) image_type : Type d’image (abrégé, nom complet) slice_no : Numéro de la tranche (1 origine, par défaut : 1) Retourne : Une instance d’ImageChunk correspondant aux critères spécifiés ; sinon, None

Source code in .build\fr\isdreader\isd_root.py
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
def GetImage(self, *, ch: int, gate: int, image_type: str, slice_no: Optional[int] = 1) -> Optional[ImageChunk]:
    """
    Méthode pour récupérer directement un ImageChunk
    Arguments :
      ch : Numéro du canal (1 origine)
      gate : Numéro du DataGate (1 origine)
      image_type : Type d’image (abrégé, nom complet)
      slice_no : Numéro de la tranche (1 origine, par défaut : 1)
    Retourne :
      Une instance d’ImageChunk correspondant aux critères spécifiés ; sinon, None
    """
    chObj = self.GetCh(ch)
    if chObj is None:
        return None
    gateObj = chObj.GetDataGate(gate)
    if gateObj is None:
        return None
    imgObj = gateObj.GetImage(image_type, slice_no)
    return imgObj

__init__(*, isd_path, logger=None)

Initialise un objet IsdReader à partir du dossier ISD spécifié. Arguments : isd_path : Chemin d'accès au dossier ISD (chaîne de caractères ou pathlib.Path). logger : Instance de journalisation facultative. Journalisation par défaut si None. Lève : TypeError : Si isd_path n'est ni une chaîne de caractères ni un chemin. IsdNotFound : Si le dossier ISD est introuvable. DescriptionNotFound : Si le fichier Description.xml est introuvable dans le dossier ISD.

Source code in .build\fr\isdreader\isd_root.py
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
def __init__(self, *, isd_path: Union[str, Path], logger: Optional[logging.Logger] = None) -> None:
    """
    Initialise un objet IsdReader à partir du dossier ISD spécifié.
    Arguments :
      isd_path : Chemin d'accès au dossier ISD (chaîne de caractères ou pathlib.Path).
      logger : Instance de journalisation facultative. Journalisation par défaut si None.
    Lève :
      TypeError : Si isd_path n'est ni une chaîne de caractères ni un chemin.
      IsdNotFound : Si le dossier ISD est introuvable.
      DescriptionNotFound : Si le fichier Description.xml est introuvable dans le dossier ISD.
    """
    if not isinstance(isd_path, (str, Path)):
        raise TypeError("isd_path must be str or pathlib.Path")

    self.path = Path(isd_path)
    if not self.path.exists() or not self.path.is_dir():
        raise IsdNotFound(f"ISD folder not found: {isd_path}")

    self.description_path = self.path / "Description.xml"
    if not self.description_path.exists():
        raise DescriptionNotFound(f"Description.xml not found in: {self.path}")

    tree = etree.parse(self.description_path)
    root = tree.getroot()
    isd_root = Path(self.description_path).parent

    self._scan_type = root.findtext("Info/ScanType")
    self._width_pixel = int(root.findtext("Info/WidthPixel") or 0)
    self._height_pixel = int(root.findtext("Info/HeightPixel") or 0)

    wp = root.find("Info/WidthPhysical")
    if wp is not None:
        try:
            self._width_physical = float(wp.text.strip())
        except Exception:
            self._width_physical = None
        self._width_physical_unit = wp.get("Unit")
    else:
        self._width_physical = None
        self._width_physical_unit = None

    hp = root.find("Info/HeightPhysical")
    if hp is not None:
        try:
            self._height_physical = float(hp.text.strip())
        except Exception:
            self._height_physical = None
        self._height_physical_unit = hp.get("Unit")
    else:
        self._height_physical = None
        self._height_physical_unit = None

    self._channels: List[ChChunk] = []
    for ch_elem in root.findall("Channel"):
        self._channels.append(ChChunk(root, ch_elem, isd_root, self._width_pixel or 0, self._height_pixel or 0))

    self._root_elem = root

    self.logger = logger or logging.getLogger(__name__)

__repr__()

Cette fonction renvoie un résumé sous forme de chaîne de caractères de l'IsdReader. Renvoie : Une chaîne de caractères contenant la taille et le nombre de canaux disponibles.

Source code in .build\fr\isdreader\isd_root.py
87
88
89
90
91
92
93
94
95
96
97
98
99
def __repr__(self) -> str:
    """
    Cette fonction renvoie un résumé sous forme de chaîne de caractères de l'IsdReader.
    Renvoie :
      Une chaîne de caractères contenant la taille et le nombre de canaux disponibles.
    """
    parts: List[str] = []
    if self._width_pixel is not None and self._height_pixel is not None:
        parts.append(f"size={self._width_pixel}x{self._height_pixel}")
    chs = self.GetCh()
    if chs:
        parts.append(f"channels={','.join(str(int(c)) for c in chs)}")
    return f"IsdReader[{', '.join(parts)}]"

Modules principaux

ChChunk

Classe représentant un canal pouvant contenir plusieurs DataGates. Cette classe correspond au canal ultrasonore physique au sein du système d'acquisition.

Source code in .build\fr\isdreader\chunks.py
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
class ChChunk:
    """
    Classe représentant un canal pouvant contenir plusieurs DataGates.
    Cette classe correspond au canal ultrasonore physique au sein du système d'acquisition.
    """
    def __init__(self, root_elem: etree.Element, ch_elem: etree.Element, isd_root: Path, width: int, height: int):
        """
        Initialiser l'instance ChChunk.
        Arguments :
          root_elem : Élément XML racine de Description.xml
          ch_elem : Élément XML du canal
          isd_root : Chemin vers le dossier racine ISD
          width : Largeur de l'image (en pixels)
          height : Hauteur de l'image (en pixels)
        """
        self._elem = ch_elem
        self._ch_id_xml: int = int(ch_elem.get("id", "-1"))
        self._ch: Optional[int] = (self._ch_id_xml + 1) if self._ch_id_xml != -1 else None
        self._channel_name: Optional[str] = ch_elem.get("Name")
        self._sampling_freq_mhz: Optional[float] = float(ch_elem.get("SamplingFreqMHz") or 0)
        self._datagates: List[DataGateChunk] = []
        for dg in ch_elem.findall(".//DataGate"):
            self._datagates.append(
                DataGateChunk(
                    root_elem,
                    ch_elem,
                    dg,
                    isd_root,
                    self._ch,
                    self._channel_name,
                    width,
                    height,
                    self._sampling_freq_mhz or 0.0,
                )
            )
        self._assigned: Dict[str, Any] = {}
# --------------------------------------------------------------------------------------------------------
    def list_datagates(self) -> List[int]:
        """
        Affiche la liste de tous les numéros DataGate disponibles.
        Retourne :
          Liste des numéros DataGate (1 origine)
        """
        return [dg._dg_public for dg in self._datagates if dg._dg_public is not None]
# --------------------------------------------------------------------------------------------------------
    def GetDataGate(self, data_gate: Optional[int] = None):
        """
        Récupère une instance de DataGateChunk ou liste tous les DataGates.
        Arguments :
          data_gate : si None, liste les numéros des DataGates ; sinon, retourne le DataGateChunk correspondant.
        Retourne :
          Si data_gate est None, une liste de numéros de DataGate ; sinon, une instance de DataGateChunk ou None.
        """
        if data_gate is None:
            return self.list_datagates()
        dg_num = int(data_gate)
        for dg in self._datagates:
            if dg._dg_public == dg_num:
                return dg
        return None
# --------------------------------------------------------------------------------------------------------
    def __repr__(self) -> str:
        """
        Renvoie un résumé sous forme de chaîne de caractères de ce ChChunk.
        Renvoie :
          Une représentation sous forme de chaîne de caractères comprenant le numéro de canal, le nom et le DataGate.
        """
        return f"ChChunk[ch={self._ch}, name={self._channel_name}, data_gates={self.list_datagates()}]"

GetDataGate(data_gate=None)

Récupère une instance de DataGateChunk ou liste tous les DataGates. Arguments : data_gate : si None, liste les numéros des DataGates ; sinon, retourne le DataGateChunk correspondant. Retourne : Si data_gate est None, une liste de numéros de DataGate ; sinon, une instance de DataGateChunk ou None.

Source code in .build\fr\isdreader\chunks.py
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
def GetDataGate(self, data_gate: Optional[int] = None):
    """
    Récupère une instance de DataGateChunk ou liste tous les DataGates.
    Arguments :
      data_gate : si None, liste les numéros des DataGates ; sinon, retourne le DataGateChunk correspondant.
    Retourne :
      Si data_gate est None, une liste de numéros de DataGate ; sinon, une instance de DataGateChunk ou None.
    """
    if data_gate is None:
        return self.list_datagates()
    dg_num = int(data_gate)
    for dg in self._datagates:
        if dg._dg_public == dg_num:
            return dg
    return None

__init__(root_elem, ch_elem, isd_root, width, height)

Initialiser l'instance ChChunk. Arguments : root_elem : Élément XML racine de Description.xml ch_elem : Élément XML du canal isd_root : Chemin vers le dossier racine ISD width : Largeur de l'image (en pixels) height : Hauteur de l'image (en pixels)

Source code in .build\fr\isdreader\chunks.py
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
def __init__(self, root_elem: etree.Element, ch_elem: etree.Element, isd_root: Path, width: int, height: int):
    """
    Initialiser l'instance ChChunk.
    Arguments :
      root_elem : Élément XML racine de Description.xml
      ch_elem : Élément XML du canal
      isd_root : Chemin vers le dossier racine ISD
      width : Largeur de l'image (en pixels)
      height : Hauteur de l'image (en pixels)
    """
    self._elem = ch_elem
    self._ch_id_xml: int = int(ch_elem.get("id", "-1"))
    self._ch: Optional[int] = (self._ch_id_xml + 1) if self._ch_id_xml != -1 else None
    self._channel_name: Optional[str] = ch_elem.get("Name")
    self._sampling_freq_mhz: Optional[float] = float(ch_elem.get("SamplingFreqMHz") or 0)
    self._datagates: List[DataGateChunk] = []
    for dg in ch_elem.findall(".//DataGate"):
        self._datagates.append(
            DataGateChunk(
                root_elem,
                ch_elem,
                dg,
                isd_root,
                self._ch,
                self._channel_name,
                width,
                height,
                self._sampling_freq_mhz or 0.0,
            )
        )
    self._assigned: Dict[str, Any] = {}

__repr__()

Renvoie un résumé sous forme de chaîne de caractères de ce ChChunk. Renvoie : Une représentation sous forme de chaîne de caractères comprenant le numéro de canal, le nom et le DataGate.

Source code in .build\fr\isdreader\chunks.py
401
402
403
404
405
406
407
def __repr__(self) -> str:
    """
    Renvoie un résumé sous forme de chaîne de caractères de ce ChChunk.
    Renvoie :
      Une représentation sous forme de chaîne de caractères comprenant le numéro de canal, le nom et le DataGate.
    """
    return f"ChChunk[ch={self._ch}, name={self._channel_name}, data_gates={self.list_datagates()}]"

list_datagates()

Affiche la liste de tous les numéros DataGate disponibles. Retourne : Liste des numéros DataGate (1 origine)

Source code in .build\fr\isdreader\chunks.py
377
378
379
380
381
382
383
def list_datagates(self) -> List[int]:
    """
    Affiche la liste de tous les numéros DataGate disponibles.
    Retourne :
      Liste des numéros DataGate (1 origine)
    """
    return [dg._dg_public for dg in self._datagates if dg._dg_public is not None]

DataGateChunk

Classe représentant un DataGate au sein d'un canal. Notez qu'un DataGate peut contenir plusieurs images de coupe.

Source code in .build\fr\isdreader\chunks.py
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
class DataGateChunk:
    """
    Classe représentant un DataGate au sein d'un canal.
    Notez qu'un DataGate peut contenir plusieurs images de coupe.
    """
# --------------------------------------------------------------------------------------------------------
    def __init__(
        self,
        root_elem: etree.Element,
        ch_elem: etree.Element,
        dg_elem: etree.Element,
        isd_root: Path,
        ch_public: Optional[int],
        ch_name: Optional[str],
        width: int,
        height: int,
        sampling_freq_mhz: float,
    ):
        """
        Initialiser une instance DataGateChunk
        Arguments :
          root_elem : Élément XML racine de Description.xml
          ch_elem : Élément XML du canal
          dg_elem : Élément XML DataGate
          isd_root : Chemin d'accès au dossier racine ISD
          ch_public : Numéro du canal public (1 origine)
          ch_name : Nom du canal
          width : Largeur de l'image (en pixels)
          height : Hauteur de l'image (en pixels)
          sampling_freq_mhz : Fréquence d'échantillonnage (MHz)
        """
        self._elem = dg_elem
        self._dg_id_xml: int = int(dg_elem.get("id", "-1"))
        self._dg_public: Optional[int] = (self._dg_id_xml - 1) if self._dg_id_xml != -1 else None
        self._data_gate_name = dg_elem.get("Name")
        self._image_elems: List[etree.Element] = dg_elem.findall(".//Image")
        self._images: Dict[Tuple[int, str], ImageChunk] = {}
        self._root_elem = root_elem
        self._ch_elem = ch_elem
        self._isd_root = isd_root
        self._ch_public = ch_public
        self._ch_name = ch_name
        self._width = width
        self._height = height
        self._sampling_freq_mhz = sampling_freq_mhz
        self._assigned: Dict[str, Any] = {}
# --------------------------------------------------------------------------------------------------------
    def _ensure_image(self, img_elem: etree.Element, type_abbr: str, type_elem: etree.Element) -> ImageChunk:
        """
        Vérifie l'existence d'un ImageChunk pour l'élément image et le type spécifiés.
        Arguments :
          img_elem : Élément XML image
          type_abbr : Abréviation du type d'image
          type_elem : Élément XML d'un type d'image spécifique
        Retourne :
          Instance d'ImageChunk
        """
        try:
            img_id = int(img_elem.get("id", "0"))
        except Exception:
            img_id = 0
        key = (img_id, type_abbr)
        if key in self._images:
            return self._images[key]
        img = ImageChunk(
            root_elem=self._root_elem,
            ch_elem=self._ch_elem,
            dg_elem=self._elem,
            img_elem=img_elem,
            isd_root=self._isd_root,
            ch_public=self._ch_public,
            dg_xml_id=self._dg_id_xml,
            type_abbr=type_abbr,
            type_elem=type_elem,
        )
        self._images[key] = img
        return img
# --------------------------------------------------------------------------------------------------------
    def list_images(self) -> List[int]:
        """
        Affiche la liste de tous les numéros de tranches disponibles (1 origine).
        Retourne :
          Liste des numéros de tranches
        """
        res: List[int] = []
        for el in self._image_elems:
            try:
                res.append(int(el.get("id", "0")) + 1)
            except Exception:
                continue
        return res
# --------------------------------------------------------------------------------------------------------
    def GetSlice(self, slice_no: Optional[int] = None):
        """
        Afficher toutes les tranches.
        Arguments :
          slice_no : Si None, afficher tous les numéros de tranche ; sinon, une exception TypeError est levée.
        Retour :
          Si slice_no est None, afficher les numéros de tranche.
        Lève :
          TypeError : Si slice_no est spécifié.
        """
        if slice_no is None:
            return self.list_images()
        raise TypeError("GetSlice with slice_no does not return ImageChunk; use GetImage(image_type, slice_no)")
# --------------------------------------------------------------------------------------------------------
    def ImageTypes(self) -> str:
        """
        Renvoie une chaîne de caractères décrivant les types d'images disponibles.
        Renvoie :
          une chaîne de caractères contenant les noms abrégés et complets des types d'images, séparés par des virgules.
        """
        return ", ".join(f"{k}: {_IMAGE_TYPE_MAP[k]}" for k in _IMAGE_TYPE_MAP)
# --------------------------------------------------------------------------------------------------------
    def GetImage(self, image_type: str, slice_no: Optional[int] = 1) -> Optional[ImageChunk]:
        """
        Renvoie une instance ImageChunk du type et de la tranche spécifiés.
        Arguments :
          image_type : Type d’image (nom abrégé ou complet)
          slice_no : Numéro de la tranche (origine 1, par défaut : 1)
        Renvoie :
          Une instance ImageChunk si elle existe, None sinon
        """
        idx = int(slice_no) - 1
        for el in self._image_elems:
            try:
                if int(el.get("id", "-1")) == idx:
                    abbr, t = _select_type_elem_for_image(el, image_type)
                    return self._ensure_image(el, abbr, t)
            except Exception:
                continue
        return None
# --------------------------------------------------------------------------------------------------------
    def __repr__(self) -> str:
        """
        Cette fonction renvoie un résumé sous forme de chaîne de caractères de ce DataGateChunk.
        Renvoie :
          Une représentation sous forme de chaîne de caractères comprenant l’identifiant, le nom et les images disponibles.
        """
        imgs = self.list_images()
        name = self._data_gate_name or ""
        return f"DataGateChunk[id={self._dg_public}, name={name}, images={imgs}]"

GetImage(image_type, slice_no=1)

Renvoie une instance ImageChunk du type et de la tranche spécifiés. Arguments : image_type : Type d’image (nom abrégé ou complet) slice_no : Numéro de la tranche (origine 1, par défaut : 1) Renvoie : Une instance ImageChunk si elle existe, None sinon

Source code in .build\fr\isdreader\chunks.py
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
def GetImage(self, image_type: str, slice_no: Optional[int] = 1) -> Optional[ImageChunk]:
    """
    Renvoie une instance ImageChunk du type et de la tranche spécifiés.
    Arguments :
      image_type : Type d’image (nom abrégé ou complet)
      slice_no : Numéro de la tranche (origine 1, par défaut : 1)
    Renvoie :
      Une instance ImageChunk si elle existe, None sinon
    """
    idx = int(slice_no) - 1
    for el in self._image_elems:
        try:
            if int(el.get("id", "-1")) == idx:
                abbr, t = _select_type_elem_for_image(el, image_type)
                return self._ensure_image(el, abbr, t)
        except Exception:
            continue
    return None

GetSlice(slice_no=None)

Afficher toutes les tranches. Arguments : slice_no : Si None, afficher tous les numéros de tranche ; sinon, une exception TypeError est levée. Retour : Si slice_no est None, afficher les numéros de tranche. Lève : TypeError : Si slice_no est spécifié.

Source code in .build\fr\isdreader\chunks.py
288
289
290
291
292
293
294
295
296
297
298
299
300
def GetSlice(self, slice_no: Optional[int] = None):
    """
    Afficher toutes les tranches.
    Arguments :
      slice_no : Si None, afficher tous les numéros de tranche ; sinon, une exception TypeError est levée.
    Retour :
      Si slice_no est None, afficher les numéros de tranche.
    Lève :
      TypeError : Si slice_no est spécifié.
    """
    if slice_no is None:
        return self.list_images()
    raise TypeError("GetSlice with slice_no does not return ImageChunk; use GetImage(image_type, slice_no)")

ImageTypes()

Renvoie une chaîne de caractères décrivant les types d'images disponibles. Renvoie : une chaîne de caractères contenant les noms abrégés et complets des types d'images, séparés par des virgules.

Source code in .build\fr\isdreader\chunks.py
302
303
304
305
306
307
308
def ImageTypes(self) -> str:
    """
    Renvoie une chaîne de caractères décrivant les types d'images disponibles.
    Renvoie :
      une chaîne de caractères contenant les noms abrégés et complets des types d'images, séparés par des virgules.
    """
    return ", ".join(f"{k}: {_IMAGE_TYPE_MAP[k]}" for k in _IMAGE_TYPE_MAP)

__init__(root_elem, ch_elem, dg_elem, isd_root, ch_public, ch_name, width, height, sampling_freq_mhz)

Initialiser une instance DataGateChunk Arguments : root_elem : Élément XML racine de Description.xml ch_elem : Élément XML du canal dg_elem : Élément XML DataGate isd_root : Chemin d'accès au dossier racine ISD ch_public : Numéro du canal public (1 origine) ch_name : Nom du canal width : Largeur de l'image (en pixels) height : Hauteur de l'image (en pixels) sampling_freq_mhz : Fréquence d'échantillonnage (MHz)

Source code in .build\fr\isdreader\chunks.py
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
def __init__(
    self,
    root_elem: etree.Element,
    ch_elem: etree.Element,
    dg_elem: etree.Element,
    isd_root: Path,
    ch_public: Optional[int],
    ch_name: Optional[str],
    width: int,
    height: int,
    sampling_freq_mhz: float,
):
    """
    Initialiser une instance DataGateChunk
    Arguments :
      root_elem : Élément XML racine de Description.xml
      ch_elem : Élément XML du canal
      dg_elem : Élément XML DataGate
      isd_root : Chemin d'accès au dossier racine ISD
      ch_public : Numéro du canal public (1 origine)
      ch_name : Nom du canal
      width : Largeur de l'image (en pixels)
      height : Hauteur de l'image (en pixels)
      sampling_freq_mhz : Fréquence d'échantillonnage (MHz)
    """
    self._elem = dg_elem
    self._dg_id_xml: int = int(dg_elem.get("id", "-1"))
    self._dg_public: Optional[int] = (self._dg_id_xml - 1) if self._dg_id_xml != -1 else None
    self._data_gate_name = dg_elem.get("Name")
    self._image_elems: List[etree.Element] = dg_elem.findall(".//Image")
    self._images: Dict[Tuple[int, str], ImageChunk] = {}
    self._root_elem = root_elem
    self._ch_elem = ch_elem
    self._isd_root = isd_root
    self._ch_public = ch_public
    self._ch_name = ch_name
    self._width = width
    self._height = height
    self._sampling_freq_mhz = sampling_freq_mhz
    self._assigned: Dict[str, Any] = {}

__repr__()

Cette fonction renvoie un résumé sous forme de chaîne de caractères de ce DataGateChunk. Renvoie : Une représentation sous forme de chaîne de caractères comprenant l’identifiant, le nom et les images disponibles.

Source code in .build\fr\isdreader\chunks.py
329
330
331
332
333
334
335
336
337
def __repr__(self) -> str:
    """
    Cette fonction renvoie un résumé sous forme de chaîne de caractères de ce DataGateChunk.
    Renvoie :
      Une représentation sous forme de chaîne de caractères comprenant l’identifiant, le nom et les images disponibles.
    """
    imgs = self.list_images()
    name = self._data_gate_name or ""
    return f"DataGateChunk[id={self._dg_public}, name={name}, images={imgs}]"

list_images()

Affiche la liste de tous les numéros de tranches disponibles (1 origine). Retourne : Liste des numéros de tranches

Source code in .build\fr\isdreader\chunks.py
274
275
276
277
278
279
280
281
282
283
284
285
286
def list_images(self) -> List[int]:
    """
    Affiche la liste de tous les numéros de tranches disponibles (1 origine).
    Retourne :
      Liste des numéros de tranches
    """
    res: List[int] = []
    for el in self._image_elems:
        try:
            res.append(int(el.get("id", "0")) + 1)
        except Exception:
            continue
    return res

ImageChunk

Classe contenant les données d'une image (métadonnées incluses) au sein de DataGate. Cette classe stocke toutes les métadonnées et permet d'accéder aux données binaires de l'image.

Source code in .build\fr\isdreader\chunks.py
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
class ImageChunk:
    """
    Classe contenant les données d'une image (métadonnées incluses) au sein de DataGate.
    Cette classe stocke toutes les métadonnées et permet d'accéder aux données binaires de l'image.
    """
# --------------------------------------------------------------------------------------------------------
    def __init__(
        self,
        root_elem: etree.Element,
        ch_elem: etree.Element,
        dg_elem: etree.Element,
        img_elem: etree.Element,
        isd_root: Path,
        ch_public: int,
        dg_xml_id: int,
        type_abbr: str,
        type_elem: etree.Element,
    ):
        """
        Initialiser cette instance ImageChunk.
        Arguments :
          root_elem : Élément XML racine de Description.xml
          ch_elem : Élément XML du canal
          dg_elem : Élément XML DataGate
          img_elem : Élément XML de l’image
          isd_root : Chemin d’accès au dossier racine ISD
          ch_public : Numéro du canal public (1 origine)
          dg_xml_id : Attribut d’identifiant XML DataGate
          type_abbr : Abréviation du type d’image (« PP », « AP », etc.)
          type_elem : Élément XML d’un type d’image spécifique
        """
        self._root_elem = root_elem
        self._ch_elem = ch_elem
        self._dg_elem = dg_elem
        self._img_elem = img_elem

        self.image_name: str = img_elem.get("Name", "01")

        self._type_elem = type_elem
        self._type_abbr = type_abbr

        self._isd_root = Path(isd_root)
        self._ch_public = ch_public
        self._dg_xml_id = dg_xml_id
        self._width = int(root_elem.findtext("Info/WidthPixel") or 0)
        self._height = int(root_elem.findtext("Info/HeightPixel") or 0)

        self._inject_properties_from_definitions()

        self._img_array: Optional[np.ndarray] = None
# --------------------------------------------------------------------------------------------------------
    def _inject_properties_from_definitions(self) -> None:
        """PROPERTY_DEFINITIONSからメタデータプロパティをこのインスタンスに与える"""
        root = self._root_elem
        ch_letter = CH_NUM_TO_LETTER.get(int(self._ch_public), "")
        dg = self._dg_elem
        type_elem = self._type_elem

        for prop_key in PROPERTY_DEFINITIONS.keys():
            final_key = prop_key.replace("$", ch_letter) if "$" in prop_key else prop_key
            if not hasattr(self, final_key):
                setattr(self, final_key, None)

        for prop_name, spec in PROPERTY_DEFINITIONS.items():
            kind = spec.get("kind")
            if kind == "info":
                node = root.find(f".//Info/{spec['path']}")
                if node is not None and node.text:
                    setattr(self, prop_name, node.text.strip())
            elif kind == "parameter":
                v = _find_category_item(root, spec["category"], spec["item"])
                if v is not None:
                    setattr(self, prop_name, v)
            elif kind == "channel_param":
                v = _find_channel_category_item(root, ch_letter, spec["category_base"], spec["item"])
                if v is not None:
                    setattr(self, prop_name, v)
            elif kind == "parameter_in_ch":
                v = _find_parameter_in_ch(root, spec["category"], spec["item_template"], ch_letter)
                if v is not None:
                    prop_final = prop_name.replace("$", ch_letter)
                    setattr(self, prop_final, v)
            elif kind == "gate_param":
                category_base = spec.get("category_base", "Gate - Ch.$")
                dg_name = dg.get("Name") if dg is not None else None
                v = _find_category_item_for_gate(root, category_base, ch_letter, dg_name, spec["item"])
                if v is not None:
                    setattr(self, prop_name, v)
            elif kind == "image_type":
                v = _find_image_type_value(type_elem, spec["key"])
                if v is not None:
                    setattr(self, prop_name, v)
# --------------------------------------------------------------------------------------------------------
    def build_metadata_args(self) -> Tuple[int, int, int]:
        """
        Construit les paramètres à transmettre à binary_loader à partir de la propriété ImageChunk.
        Retourne :
          Un tuple (largeur, hauteur, taille_données) pour le chargement binaire.
        """
        width = int(getattr(self, "WidthPixel", self._width) or self._width)
        height = int(getattr(self, "HeightPixel", self._height) or self._height)
        data_size = int(getattr(self, "ImgDataSize", 8) or 8)
        return width, height, data_size
# --------------------------------------------------------------------------------------------------------
    def load_image(self, y_flipped: bool = True) -> np.ndarray:
        """
        Lit les données binaires d'une image et les renvoie sous forme de tableau NumPy 2D.
        Arguments :
          y_flipped : Si la valeur est True, l'image lue est inversée verticalement (par défaut : True).
        Renvoie :
          Un tableau NumPy 2D d'images.
        Lève :
          MiscellaneousError : Si le nom du fichier image est introuvable.
          BinaryFileNotFound : Si le fichier binaire n'existe pas.
        """
        fn = _find_image_type_value(self._type_elem, "FileName")
        if fn is None:
            raise MiscellaneousError("Image file name not found")
        if not fn.casefold().endswith(".bin"):
            fn = fn + ".bin"
        resolver = _PathResolver(self._isd_root)
        bin_path = resolver.resolve_binary_path(
            ch=self._ch_public,
            data_gate=(self._dg_xml_id - 1),
            img_name=self.image_name,
            image_type=fn,
        )
        if not bin_path.exists():
            raise BinaryFileNotFound(f"Binary file not found: {bin_path}")

        width, height, data_size = self.build_metadata_args()

        loader = _BinaryLoader(logger=_logger)
        arr = loader.load_as_2d_array(bin_path, width, height, data_size)

        self._img_array = np.flipud(arr) if y_flipped else arr
        return self._img_array
# --------------------------------------------------------------------------------------------------------
    @property
    def img_array(self) -> np.ndarray:
        """
        Accéder au tableau d'images chargé.
        Retourne :
          Tableau NumPy 2D chargé
        Lève :
          MiscellaneousError : Si l'image n'a pas encore été chargée.
        """
        if self._img_array is None:
            raise MiscellaneousError("Image not loaded. Call load_image() first")
        return self._img_array
# --------------------------------------------------------------------------------------------------------
    def __repr__(self) -> str:
        """
        Renvoie un résumé sous forme de chaîne de caractères de cet ImageChunk.
        Renvoie :
          Une représentation sous forme de chaîne de caractères contenant toutes les propriétés injectées.
        """
        parts: List[str] = []
        ch_letter = CH_NUM_TO_LETTER.get(int(self._ch_public), "")
        for key in PROPERTY_DEFINITIONS.keys():
            final_key = key.replace("$", ch_letter) if "$" in key else key
            val = getattr(self, final_key, None)
            parts.append(f"{final_key}={val!r}")
        return f"ImageChunk[name={self.image_name}, type={self._type_abbr}, {', '.join(parts)}]"

img_array property

Accéder au tableau d'images chargé. Retourne : Tableau NumPy 2D chargé Lève : MiscellaneousError : Si l'image n'a pas encore été chargée.

__init__(root_elem, ch_elem, dg_elem, img_elem, isd_root, ch_public, dg_xml_id, type_abbr, type_elem)

Initialiser cette instance ImageChunk. Arguments : root_elem : Élément XML racine de Description.xml ch_elem : Élément XML du canal dg_elem : Élément XML DataGate img_elem : Élément XML de l’image isd_root : Chemin d’accès au dossier racine ISD ch_public : Numéro du canal public (1 origine) dg_xml_id : Attribut d’identifiant XML DataGate type_abbr : Abréviation du type d’image (« PP », « AP », etc.) type_elem : Élément XML d’un type d’image spécifique

Source code in .build\fr\isdreader\chunks.py
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
def __init__(
    self,
    root_elem: etree.Element,
    ch_elem: etree.Element,
    dg_elem: etree.Element,
    img_elem: etree.Element,
    isd_root: Path,
    ch_public: int,
    dg_xml_id: int,
    type_abbr: str,
    type_elem: etree.Element,
):
    """
    Initialiser cette instance ImageChunk.
    Arguments :
      root_elem : Élément XML racine de Description.xml
      ch_elem : Élément XML du canal
      dg_elem : Élément XML DataGate
      img_elem : Élément XML de l’image
      isd_root : Chemin d’accès au dossier racine ISD
      ch_public : Numéro du canal public (1 origine)
      dg_xml_id : Attribut d’identifiant XML DataGate
      type_abbr : Abréviation du type d’image (« PP », « AP », etc.)
      type_elem : Élément XML d’un type d’image spécifique
    """
    self._root_elem = root_elem
    self._ch_elem = ch_elem
    self._dg_elem = dg_elem
    self._img_elem = img_elem

    self.image_name: str = img_elem.get("Name", "01")

    self._type_elem = type_elem
    self._type_abbr = type_abbr

    self._isd_root = Path(isd_root)
    self._ch_public = ch_public
    self._dg_xml_id = dg_xml_id
    self._width = int(root_elem.findtext("Info/WidthPixel") or 0)
    self._height = int(root_elem.findtext("Info/HeightPixel") or 0)

    self._inject_properties_from_definitions()

    self._img_array: Optional[np.ndarray] = None

__repr__()

Renvoie un résumé sous forme de chaîne de caractères de cet ImageChunk. Renvoie : Une représentation sous forme de chaîne de caractères contenant toutes les propriétés injectées.

Source code in .build\fr\isdreader\chunks.py
181
182
183
184
185
186
187
188
189
190
191
192
193
def __repr__(self) -> str:
    """
    Renvoie un résumé sous forme de chaîne de caractères de cet ImageChunk.
    Renvoie :
      Une représentation sous forme de chaîne de caractères contenant toutes les propriétés injectées.
    """
    parts: List[str] = []
    ch_letter = CH_NUM_TO_LETTER.get(int(self._ch_public), "")
    for key in PROPERTY_DEFINITIONS.keys():
        final_key = key.replace("$", ch_letter) if "$" in key else key
        val = getattr(self, final_key, None)
        parts.append(f"{final_key}={val!r}")
    return f"ImageChunk[name={self.image_name}, type={self._type_abbr}, {', '.join(parts)}]"

build_metadata_args()

Construit les paramètres à transmettre à binary_loader à partir de la propriété ImageChunk. Retourne : Un tuple (largeur, hauteur, taille_données) pour le chargement binaire.

Source code in .build\fr\isdreader\chunks.py
123
124
125
126
127
128
129
130
131
132
def build_metadata_args(self) -> Tuple[int, int, int]:
    """
    Construit les paramètres à transmettre à binary_loader à partir de la propriété ImageChunk.
    Retourne :
      Un tuple (largeur, hauteur, taille_données) pour le chargement binaire.
    """
    width = int(getattr(self, "WidthPixel", self._width) or self._width)
    height = int(getattr(self, "HeightPixel", self._height) or self._height)
    data_size = int(getattr(self, "ImgDataSize", 8) or 8)
    return width, height, data_size

load_image(y_flipped=True)

Lit les données binaires d'une image et les renvoie sous forme de tableau NumPy 2D. Arguments : y_flipped : Si la valeur est True, l'image lue est inversée verticalement (par défaut : True). Renvoie : Un tableau NumPy 2D d'images. Lève : MiscellaneousError : Si le nom du fichier image est introuvable. BinaryFileNotFound : Si le fichier binaire n'existe pas.

Source code in .build\fr\isdreader\chunks.py
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
def load_image(self, y_flipped: bool = True) -> np.ndarray:
    """
    Lit les données binaires d'une image et les renvoie sous forme de tableau NumPy 2D.
    Arguments :
      y_flipped : Si la valeur est True, l'image lue est inversée verticalement (par défaut : True).
    Renvoie :
      Un tableau NumPy 2D d'images.
    Lève :
      MiscellaneousError : Si le nom du fichier image est introuvable.
      BinaryFileNotFound : Si le fichier binaire n'existe pas.
    """
    fn = _find_image_type_value(self._type_elem, "FileName")
    if fn is None:
        raise MiscellaneousError("Image file name not found")
    if not fn.casefold().endswith(".bin"):
        fn = fn + ".bin"
    resolver = _PathResolver(self._isd_root)
    bin_path = resolver.resolve_binary_path(
        ch=self._ch_public,
        data_gate=(self._dg_xml_id - 1),
        img_name=self.image_name,
        image_type=fn,
    )
    if not bin_path.exists():
        raise BinaryFileNotFound(f"Binary file not found: {bin_path}")

    width, height, data_size = self.build_metadata_args()

    loader = _BinaryLoader(logger=_logger)
    arr = loader.load_as_2d_array(bin_path, width, height, data_size)

    self._img_array = np.flipud(arr) if y_flipped else arr
    return self._img_array

CH_NUM_TO_LETTER = {1: 'A', 2: 'B', 3: 'C', 4: 'D'} module-attribute

Correspondance entre les types d'images abrégés et les noms complets

BinaryFileNotFound

Bases: Exception

Une exception se produit si le fichier binaire spécifié est introuvable dans le dossier ISD.

Source code in .build\fr\isdreader\isd_helper.py
55
56
57
58
59
class BinaryFileNotFound(Exception):
    """
    Une exception se produit si le fichier binaire spécifié est introuvable dans le dossier ISD.
    """
    pass

DescriptionNotFound

Bases: Exception

Une exception se produit si le fichier Description.xml est introuvable dans le dossier ISD.

Source code in .build\fr\isdreader\isd_helper.py
41
42
43
44
45
class DescriptionNotFound(Exception):
    """
    Une exception se produit si le fichier Description.xml est introuvable dans le dossier ISD.
    """
    pass

InsufficientMetaData

Bases: Exception

Une exception se produit lorsqu'il n'y a pas suffisamment de métadonnées pour poursuivre le traitement.

Source code in .build\fr\isdreader\isd_helper.py
48
49
50
51
52
class InsufficientMetaData(Exception):
    """
    Une exception se produit lorsqu'il n'y a pas suffisamment de métadonnées pour poursuivre le traitement.
    """
    pass

InvalidChannel

Bases: Exception

Une exception se produit lorsque l'index du canal spécifié est invalide.

Source code in .build\fr\isdreader\isd_helper.py
13
14
15
16
17
class InvalidChannel(Exception):
    """
    Une exception se produit lorsque l'index du canal spécifié est invalide.
    """
    pass

InvalidDataGate

Bases: Exception

Une exception se produit lorsque l'index de la porte de données spécifié est invalide.

Source code in .build\fr\isdreader\isd_helper.py
20
21
22
23
24
class InvalidDataGate(Exception):
    """
    Une exception se produit lorsque l'index de la porte de données spécifié est invalide.
    """
    pass

InvalidSliceNo

Bases: Exception

Une exception se produit lorsque le numéro de tranche spécifié est invalide.

Source code in .build\fr\isdreader\isd_helper.py
27
28
29
30
31
class InvalidSliceNo(Exception):
    """
    Une exception se produit lorsque le numéro de tranche spécifié est invalide.
    """
    pass

IsdNotFound

Bases: Exception

Une exception se produit lorsque le dossier ISD spécifié n'existe pas.

Source code in .build\fr\isdreader\isd_helper.py
34
35
36
37
38
class IsdNotFound(Exception):
    """
    Une exception se produit lorsque le dossier ISD spécifié n'existe pas.
    """
    pass

MiscellaneousError

Bases: Exception

Des exceptions qui surviennent pour d'autres raisons inconnues

Source code in .build\fr\isdreader\isd_helper.py
62
63
64
65
66
class MiscellaneousError(Exception):
    """
    Des exceptions qui surviennent pour d'autres raisons inconnues
    """
    pass

IsdReader

Classe racine représentant l'intégralité du dossier ISD Cette classe est le point d'entrée principal pour accéder à tous les canaux, DataGate et images du jeu de données d'acquisition ISD. Autrement dit, il s'agit d'une classe d'objet englobant l'ensemble des données ISD. Attributs : chemin : Chemin d'accès au dossier ISD à inclure chemin_description : Chemin d'accès au fichier Description.xml (situé directement à la racine du dossier ISD) enregistreur : Instance de l'enregistreur pour cet objet

Source code in .build\fr\isdreader\isd_root.py
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
class IsdReader:
    """
    Classe racine représentant l'intégralité du dossier ISD
    Cette classe est le point d'entrée principal pour accéder à tous les canaux,
    DataGate et images du jeu de données d'acquisition ISD.
    Autrement dit, il s'agit d'une classe d'objet englobant l'ensemble des données ISD.
    Attributs :
      chemin : Chemin d'accès au dossier ISD à inclure
      chemin_description : Chemin d'accès au fichier Description.xml 
      (situé directement à la racine du dossier ISD)
      enregistreur : Instance de l'enregistreur pour cet objet
    """
# --------------------------------------------------------------------------------------------------------
    def __init__(self, *, isd_path: Union[str, Path], logger: Optional[logging.Logger] = None) -> None:
        """
        Initialise un objet IsdReader à partir du dossier ISD spécifié.
        Arguments :
          isd_path : Chemin d'accès au dossier ISD (chaîne de caractères ou pathlib.Path).
          logger : Instance de journalisation facultative. Journalisation par défaut si None.
        Lève :
          TypeError : Si isd_path n'est ni une chaîne de caractères ni un chemin.
          IsdNotFound : Si le dossier ISD est introuvable.
          DescriptionNotFound : Si le fichier Description.xml est introuvable dans le dossier ISD.
        """
        if not isinstance(isd_path, (str, Path)):
            raise TypeError("isd_path must be str or pathlib.Path")

        self.path = Path(isd_path)
        if not self.path.exists() or not self.path.is_dir():
            raise IsdNotFound(f"ISD folder not found: {isd_path}")

        self.description_path = self.path / "Description.xml"
        if not self.description_path.exists():
            raise DescriptionNotFound(f"Description.xml not found in: {self.path}")

        tree = etree.parse(self.description_path)
        root = tree.getroot()
        isd_root = Path(self.description_path).parent

        self._scan_type = root.findtext("Info/ScanType")
        self._width_pixel = int(root.findtext("Info/WidthPixel") or 0)
        self._height_pixel = int(root.findtext("Info/HeightPixel") or 0)

        wp = root.find("Info/WidthPhysical")
        if wp is not None:
            try:
                self._width_physical = float(wp.text.strip())
            except Exception:
                self._width_physical = None
            self._width_physical_unit = wp.get("Unit")
        else:
            self._width_physical = None
            self._width_physical_unit = None

        hp = root.find("Info/HeightPhysical")
        if hp is not None:
            try:
                self._height_physical = float(hp.text.strip())
            except Exception:
                self._height_physical = None
            self._height_physical_unit = hp.get("Unit")
        else:
            self._height_physical = None
            self._height_physical_unit = None

        self._channels: List[ChChunk] = []
        for ch_elem in root.findall("Channel"):
            self._channels.append(ChChunk(root, ch_elem, isd_root, self._width_pixel or 0, self._height_pixel or 0))

        self._root_elem = root

        self.logger = logger or logging.getLogger(__name__)
# --------------------------------------------------------------------------------------------------------
    def __repr__(self) -> str:
        """
        Cette fonction renvoie un résumé sous forme de chaîne de caractères de l'IsdReader.
        Renvoie :
          Une chaîne de caractères contenant la taille et le nombre de canaux disponibles.
        """
        parts: List[str] = []
        if self._width_pixel is not None and self._height_pixel is not None:
            parts.append(f"size={self._width_pixel}x{self._height_pixel}")
        chs = self.GetCh()
        if chs:
            parts.append(f"channels={','.join(str(int(c)) for c in chs)}")
        return f"IsdReader[{', '.join(parts)}]"
# --------------------------------------------------------------------------------------------------------
    def GetCh(self, ch: Optional[int] = None):
        """
        Récupère une instance de ChChunk ou liste tous les canaux.
        Arguments :
          ch : None ou un numéro de ChChunk spécifié
        Retour :
          Si ch est None, une liste des numéros de canaux disponibles est retournée ;
          sinon, l’instance de ChChunk spécifiée ou None est retournée.
        """
        if ch is None:
            return [c._ch for c in self._channels if c._ch is not None]
        for c in self._channels:
            if c._ch == int(ch):
                return c
        return None
# --------------------------------------------------------------------------------------------------------
    def GetImage(self, *, ch: int, gate: int, image_type: str, slice_no: Optional[int] = 1) -> Optional[ImageChunk]:
        """
        Méthode pour récupérer directement un ImageChunk
        Arguments :
          ch : Numéro du canal (1 origine)
          gate : Numéro du DataGate (1 origine)
          image_type : Type d’image (abrégé, nom complet)
          slice_no : Numéro de la tranche (1 origine, par défaut : 1)
        Retourne :
          Une instance d’ImageChunk correspondant aux critères spécifiés ; sinon, None
        """
        chObj = self.GetCh(ch)
        if chObj is None:
            return None
        gateObj = chObj.GetDataGate(gate)
        if gateObj is None:
            return None
        imgObj = gateObj.GetImage(image_type, slice_no)
        return imgObj

GetCh(ch=None)

Récupère une instance de ChChunk ou liste tous les canaux. Arguments : ch : None ou un numéro de ChChunk spécifié Retour : Si ch est None, une liste des numéros de canaux disponibles est retournée ; sinon, l’instance de ChChunk spécifiée ou None est retournée.

Source code in .build\fr\isdreader\isd_root.py
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
def GetCh(self, ch: Optional[int] = None):
    """
    Récupère une instance de ChChunk ou liste tous les canaux.
    Arguments :
      ch : None ou un numéro de ChChunk spécifié
    Retour :
      Si ch est None, une liste des numéros de canaux disponibles est retournée ;
      sinon, l’instance de ChChunk spécifiée ou None est retournée.
    """
    if ch is None:
        return [c._ch for c in self._channels if c._ch is not None]
    for c in self._channels:
        if c._ch == int(ch):
            return c
    return None

GetImage(*, ch, gate, image_type, slice_no=1)

Méthode pour récupérer directement un ImageChunk Arguments : ch : Numéro du canal (1 origine) gate : Numéro du DataGate (1 origine) image_type : Type d’image (abrégé, nom complet) slice_no : Numéro de la tranche (1 origine, par défaut : 1) Retourne : Une instance d’ImageChunk correspondant aux critères spécifiés ; sinon, None

Source code in .build\fr\isdreader\isd_root.py
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
def GetImage(self, *, ch: int, gate: int, image_type: str, slice_no: Optional[int] = 1) -> Optional[ImageChunk]:
    """
    Méthode pour récupérer directement un ImageChunk
    Arguments :
      ch : Numéro du canal (1 origine)
      gate : Numéro du DataGate (1 origine)
      image_type : Type d’image (abrégé, nom complet)
      slice_no : Numéro de la tranche (1 origine, par défaut : 1)
    Retourne :
      Une instance d’ImageChunk correspondant aux critères spécifiés ; sinon, None
    """
    chObj = self.GetCh(ch)
    if chObj is None:
        return None
    gateObj = chObj.GetDataGate(gate)
    if gateObj is None:
        return None
    imgObj = gateObj.GetImage(image_type, slice_no)
    return imgObj

__init__(*, isd_path, logger=None)

Initialise un objet IsdReader à partir du dossier ISD spécifié. Arguments : isd_path : Chemin d'accès au dossier ISD (chaîne de caractères ou pathlib.Path). logger : Instance de journalisation facultative. Journalisation par défaut si None. Lève : TypeError : Si isd_path n'est ni une chaîne de caractères ni un chemin. IsdNotFound : Si le dossier ISD est introuvable. DescriptionNotFound : Si le fichier Description.xml est introuvable dans le dossier ISD.

Source code in .build\fr\isdreader\isd_root.py
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
def __init__(self, *, isd_path: Union[str, Path], logger: Optional[logging.Logger] = None) -> None:
    """
    Initialise un objet IsdReader à partir du dossier ISD spécifié.
    Arguments :
      isd_path : Chemin d'accès au dossier ISD (chaîne de caractères ou pathlib.Path).
      logger : Instance de journalisation facultative. Journalisation par défaut si None.
    Lève :
      TypeError : Si isd_path n'est ni une chaîne de caractères ni un chemin.
      IsdNotFound : Si le dossier ISD est introuvable.
      DescriptionNotFound : Si le fichier Description.xml est introuvable dans le dossier ISD.
    """
    if not isinstance(isd_path, (str, Path)):
        raise TypeError("isd_path must be str or pathlib.Path")

    self.path = Path(isd_path)
    if not self.path.exists() or not self.path.is_dir():
        raise IsdNotFound(f"ISD folder not found: {isd_path}")

    self.description_path = self.path / "Description.xml"
    if not self.description_path.exists():
        raise DescriptionNotFound(f"Description.xml not found in: {self.path}")

    tree = etree.parse(self.description_path)
    root = tree.getroot()
    isd_root = Path(self.description_path).parent

    self._scan_type = root.findtext("Info/ScanType")
    self._width_pixel = int(root.findtext("Info/WidthPixel") or 0)
    self._height_pixel = int(root.findtext("Info/HeightPixel") or 0)

    wp = root.find("Info/WidthPhysical")
    if wp is not None:
        try:
            self._width_physical = float(wp.text.strip())
        except Exception:
            self._width_physical = None
        self._width_physical_unit = wp.get("Unit")
    else:
        self._width_physical = None
        self._width_physical_unit = None

    hp = root.find("Info/HeightPhysical")
    if hp is not None:
        try:
            self._height_physical = float(hp.text.strip())
        except Exception:
            self._height_physical = None
        self._height_physical_unit = hp.get("Unit")
    else:
        self._height_physical = None
        self._height_physical_unit = None

    self._channels: List[ChChunk] = []
    for ch_elem in root.findall("Channel"):
        self._channels.append(ChChunk(root, ch_elem, isd_root, self._width_pixel or 0, self._height_pixel or 0))

    self._root_elem = root

    self.logger = logger or logging.getLogger(__name__)

__repr__()

Cette fonction renvoie un résumé sous forme de chaîne de caractères de l'IsdReader. Renvoie : Une chaîne de caractères contenant la taille et le nombre de canaux disponibles.

Source code in .build\fr\isdreader\isd_root.py
87
88
89
90
91
92
93
94
95
96
97
98
99
def __repr__(self) -> str:
    """
    Cette fonction renvoie un résumé sous forme de chaîne de caractères de l'IsdReader.
    Renvoie :
      Une chaîne de caractères contenant la taille et le nombre de canaux disponibles.
    """
    parts: List[str] = []
    if self._width_pixel is not None and self._height_pixel is not None:
        parts.append(f"size={self._width_pixel}x{self._height_pixel}")
    chs = self.GetCh()
    if chs:
        parts.append(f"channels={','.join(str(int(c)) for c in chs)}")
    return f"IsdReader[{', '.join(parts)}]"