> ## Documentation Index
> Fetch the complete documentation index at: https://clickhouse.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

> Documentation du format de sortie PNG

# PNG

| Entrée | Sortie | Alias |
| ------ | ------ | ----- |
| ✗      | ✔      | ✗     |

<div id="description">
  ## Description
</div>

Affiche le résultat d’une requête sous forme d’image PNG. C’est utile comme outil de visualisation intégré.

La taille de l’image de sortie est définie par les paramètres
[`output_format_image_width`](/docs/fr/reference/settings/formats/output-format#output_format_image_width) et
[`output_format_image_height`](/docs/fr/reference/settings/formats/output-format#output_format_image_height)
(tous deux définis par défaut sur 1024). Les pixels non couverts par le résultat sont remplis de noir
(en modes `RGB` et en niveaux de gris) ou de noir transparent (en mode `RGBA`).

Le mode colorimétrique est déterminé automatiquement à partir des noms et des types des colonnes du résultat :

| Colonnes             | Mode                                                        |
| -------------------- | ----------------------------------------------------------- |
| `r`, `g`, `b`        | RGB 8 bits                                                  |
| `r`, `g`, `b`, `a`   | RGBA 8 bits                                                 |
| `v` de type entier   | niveaux de gris 8 bits                                      |
| `v` de type `Float*` | niveaux de gris 8 bits (valeurs dans `[0, 1]` → `[0, 255]`) |
| `v` de type `Bool`   | Binaire (rendu en niveaux de gris 8 bits : `0` ou `255`)    |

Les noms des colonnes sont comparés sans tenir compte de la casse. Si le mode colorimétrique ne peut pas être
déterminé de manière non ambiguë (par exemple, noms de colonnes inconnus, mélange de `v` avec `r`/`g`/`b`/`a`, ou absence de l’un de `r`/`g`/`b`),
la requête lève une exception.

Pour les canaux de pixel, les valeurs entières sont limitées à `[0, 255]` et les valeurs à virgule flottante
à `[0, 1]`, puis mises à l’échelle vers `[0, 255]`.

La position de chaque enregistrement dans l’image est déterminée selon l’un des deux modes suivants :

* **implicite** (par défaut — lorsque ni `x` ni `y` n’est présent). Chaque enregistrement correspond
  à un seul pixel ; les pixels sont remplis dans l’ordre de balayage : de gauche à droite, de haut en bas.
* **explicite** (lorsque les colonnes `x` et `y` sont présentes, toutes deux de type entier).
  Les colonnes `x` et `y` donnent les coordonnées du pixel. Les enregistrements dont les coordonnées sont en dehors
  de l’image sont ignorés silencieusement. Si plusieurs enregistrements ont les mêmes coordonnées,
  le dernier prévaut (algorithme du peintre).

<div id="example-usage">
  ## Exemple d’utilisation
</div>

<div id="implicit-rgb">
  ### Coordonnées implicites (une ligne par pixel), RVB
</div>

```sql theme={null}
SELECT
    toUInt8(x * 25) AS r,
    toUInt8(y * 25) AS g,
    toUInt8((x + y) * 12) AS b
FROM
(
    SELECT number % 10 AS x, intDiv(number, 10) AS y FROM numbers(100)
)
INTO OUTFILE 'gradient.png'
FORMAT PNG
SETTINGS output_format_image_width = 10, output_format_image_height = 10;
```

<div id="explicit-grayscale">
  ### Coordonnées explicites, niveaux de gris
</div>

```sql theme={null}
SELECT
    toInt32(x) AS x,
    toInt32(y) AS y,
    toUInt8(intensity) AS v
FROM points
INTO OUTFILE 'points.png'
FORMAT PNG
SETTINGS output_format_image_width = 512, output_format_image_height = 512;
```

<div id="animation">
  ## Animation
</div>

Si le résultat comporte une colonne `t` de type integer, le format produit un PNG animé (`APNG`) au lieu d'une
image fixe. Les enregistrements sont regroupés en images par la valeur de `t`, qui correspond au décalage temporel relatif de
l'image. Chaque image est indépendante : le canevas est vide au début de chaque image et, dans le
mode de coordonnées implicites, le curseur repart du coin supérieur gauche. La colonne `t` peut être associée
à l'un ou l'autre mode de coordonnées.

L'unité de `t` est définie par
[`output_format_image_time_multiplier_seconds`](/docs/fr/reference/settings/formats/output-format#output_format_image_time_multiplier_seconds)
et
[`output_format_image_time_divisor_seconds`](/docs/fr/reference/settings/formats/output-format#output_format_image_time_divisor_seconds) :
une unité de `t` correspond à `output_format_image_time_multiplier_seconds / output_format_image_time_divisor_seconds`
secondes. Avec les valeurs par défaut (`1` et `60`), une unité de `t` correspond à 1/60e de seconde.

Une image est affichée jusqu'au début de l'image suivante ; sa durée correspond donc à la différence entre deux valeurs consécutives
de `t`. La dernière image est affichée aussi longtemps que l'image qui la précède. L'animation se répète indéfiniment.

```sql theme={null}
SELECT
    number % 60 AS t,
    toInt32(intDiv(number, 60) % 64) AS x,
    toInt32((number * 7) % 64) AS y,
    toUInt8(255) AS v
FROM numbers(60 * 64)
INTO OUTFILE 'animation.png'
FORMAT PNG
SETTINGS output_format_image_width = 64, output_format_image_height = 64;
```

<div id="streaming-animation">
  ### Diffusion des images
</div>

Par défaut, toutes les images sont collectées en mémoire et écrites à la fin de la requête, ce qui conserve un tampon d’image
par valeur distincte de `t` et permet à `t` d’arriver dans n’importe quel ordre.

Le paramètre
[`output_format_image_streaming_animation`](/docs/fr/reference/settings/formats/output-format#output_format_image_streaming_animation)
écrit chaque image dès que la valeur suivante de `t` est reçue. Un seul tampon d’image est conservé en mémoire et
les images sont envoyées vers la sortie alors que la requête est encore en cours d’exécution, ce qui permet à un visualiseur de les afficher au fur et à mesure de leur production.
En contrepartie :

* `t` doit être non décroissant ; sinon, la requête lève une exception. Ajoutez `ORDER BY t` si nécessaire.
* Le nombre d’images n’est pas connu au moment où l’en-tête doit être écrit ; le fragment `acTL` déclare donc une limite
  supérieure plutôt que le nombre exact. Les navigateurs lisent un tel fichier, mais les décodeurs qui se fient au nombre déclaré
  (par exemple, `Pillow` et certains outils `APNG` en ligne de commande) signalent une erreur après la dernière image réelle.
  Une animation à une seule image fait exception : le résultat complet a été lu lorsque cette image est
  écrite, de sorte que le nombre est déclaré avec exactitude et que la sortie est conforme à la spécification.

Comme un protocole d’image intégré au terminal transporte l’intégralité du flux de données dans une seule charge utile, les images ne peuvent pas
parvenir au terminal de manière anticipée, et ce paramètre n’y affecte que la quantité de mémoire utilisée. Le nombre exact d’images est
corrigé dans la charge utile mise en mémoire tampon avant son envoi ; la réserve concernant la limite supérieure ne s’applique donc pas.

Une animation n’est affichée qu’en mode terminal `iterm`. Le protocole `sixel` ne peut pas représenter une
animation, et le protocole graphique Kitty n’anime qu’au moyen d’un flux distinct de commandes par image,
et non d’un flux de données animé ; il n’afficherait donc que la première image. Les deux modes rejettent un résultat contenant
une colonne `t`.

<div id="terminal-mode">
  ## Affichage des images dans le terminal
</div>

Par défaut, le format `PNG` écrit les octets bruts de l’image. Le paramètre
[`output_format_image_terminal_mode`](/docs/fr/reference/settings/formats/output-format#output_format_image_terminal_mode)
fait plutôt afficher l’image directement dans le terminal au moyen d’un protocole d’image intégré :

| Valeur      | Comportement                                                                                                                                            |
| ----------- | ------------------------------------------------------------------------------------------------------------------------------------------------------- |
| \`\` (vide) | Écrit les octets bruts de l’image (comportement par défaut).                                                                                            |
| `iterm`     | Utilise le protocole d’image intégré d’iTerm2.                                                                                                          |
| `kitty`     | Utilise le protocole graphique de Kitty. Ne peut pas afficher d’animation.                                                                              |
| `sixel`     | Utilise le protocole Sixel. L’image est réduite à une palette fixe 6×6×6 et le canal alpha, le cas échéant, est composé sur un fond noir.               |
| `auto`      | Si la sortie est un terminal, détecte ses capacités et utilise `iterm`, `kitty` ou `sixel` (dans cet ordre) ; sinon, écrit les octets bruts de l’image. |

```sql theme={null}
SELECT toUInt8(x * 25) AS r, toUInt8(y * 25) AS g, toUInt8((x + y) * 12) AS b
FROM (SELECT number % 10 AS x, intDiv(number, 10) AS y FROM numbers(100))
FORMAT PNG
SETTINGS output_format_image_width = 10, output_format_image_height = 10, output_format_image_terminal_mode = 'auto';
```

<div id="format-settings">
  ## Paramètres du format
</div>

| Paramètre                                     | Description                                                      | Par défaut  |
| --------------------------------------------- | ---------------------------------------------------------------- | ----------- |
| `output_format_image_width`                   | Largeur de l’image de sortie en pixels.                          | `1024`      |
| `output_format_image_height`                  | Hauteur de l’image de sortie en pixels.                          | `1024`      |
| `output_format_image_terminal_mode`           | Protocole intégré d’image de terminal (voir ci-dessus).          | \`\` (vide) |
| `output_format_image_time_multiplier_seconds` | Numérateur de l’unité de temps de la colonne `t`, en secondes.   | `1`         |
| `output_format_image_time_divisor_seconds`    | Dénominateur de l’unité de temps de la colonne `t`, en secondes. | `60`        |
| `output_format_image_streaming_animation`     | Écrit chaque image dès que `t` progresse (voir ci-dessus).       | `0`         |
