public/images/Get-SpectreImage.ps1

$script:CachedImages = @{}

function Get-SpectreImage {
    <#
    .SYNOPSIS
    Displays an image in the console using CanvasImage or SixelImage if the terminal supports Sixel.
 
    .DESCRIPTION
    Displays an image in the console using CanvasImage or SixelImage if the terminal supports Sixel.
    The image can be resized to a maximum width if desired.
 
    Windows Terminal supports Sixel in the [latest preview builds](https://apps.microsoft.com/detail/9n8g5rfz9xk3) so it will be available in the production builds soon 🤞
    See https://www.arewesixelyet.com/ for Sixel support status for your terminal.
 
    .PARAMETER ImagePath
    The path to the image file to be displayed, as a local path or remote path using http/https.
 
    .PARAMETER MaxWidth
    The maximum width of the image. If not specified, the image will be displayed at its original size.
 
    .EXAMPLE
    # **Example 1**
    # When Sixel is not supported the image will use the standard Canvas renderer which draws the image using character cells to represent the image.
    Get-SpectreImage -ImagePath ".\private\images\smiley.png" -MaxWidth 40
 
    .EXAMPLE
    # **Example 2**
    # For Sixel images, the image returned by `Get-SpectreImage` will render a new frame every time it's drawn so if it's an animated GIF it will appear animated if you render it repeatedly and move the cursor back to the same start position before each image output.
    #
    # ![Spectre Sixel Example](/lapras-terminal.gif)
    #
    NORECORDING
    $image = Get-SpectreImage ".\private\images\lapras-pokemon.gif" -MaxWidth 50
 
    Clear-Host
    [Console]::CursorVisible = $false
 
    for($frame = 0; $frame -lt 100; $frame++) {
        [Console]::SetCursorPosition(0, 0)
        $image | Format-SpectrePanel -Title "Frame: $frame" -Color White | Out-SpectreHost
        Start-Sleep -Milliseconds 150
    }
    #>

    [Reflection.AssemblyMetadata("title", "Get-SpectreImage")]
    param (
        [string] $ImagePath,
        [int] $MaxWidth
    )

    if ($ImagePath.StartsWith("http://") -or $ImagePath.StartsWith("https://")) {
        if (!$script:CachedImages.ContainsKey($ImagePath) -or -not (Test-Path $script:CachedImages[$ImagePath])) {
            $tempFile = New-TemporaryFile
            Invoke-WebRequest -Uri $ImagePath -UseBasicParsing -Outfile $tempFile -ProgressAction SilentlyContinue
            $script:CachedImages[$ImagePath] = $tempFile.FullName
        }
        $ImagePath = $script:CachedImages[$ImagePath]
    }

    $imagePathResolved = Resolve-Path $ImagePath
    if (-not (Test-Path $imagePathResolved)) {
        throw "The specified image path '$resolvedImagePath' does not exist."
    }

    $image = (Test-SpectreSixelSupport) ? [Spectre.Console.SixelImage]::new($imagePathResolved) : [Spectre.Console.CanvasImage]::new($imagePathResolved)

    if ($MaxWidth) {
        $image.MaxWidth = $MaxWidth
    }
    
    return $image
}