Private/Invoke-PaintGallery.ps1
[Diagnostics.CodeAnalysis.SuppressMessageAttribute("PSAvoidUsingWriteHost","",Scope="Function")] param () function Invoke-PaintGallery { <# .Synopsis Start the PwshPaint local web gallery .Description Runs a simple PowerShell web server that will show all the images drawn in the PwshPaint editor and opens your default browser to the local web page. .Example # Runs the paint gallery at the default location localhost:18383 Invoke-PaintGallery .Example # Runs the paint gallery at localhost:8080 Invoke-PaintGallery -Port 8080 #> param ( [int] $Port = 18383 ) $prefix = "http://localhost:$Port/" $contentRoot = "$PSScriptRoot/.." try { $job = Start-Job -ScriptBlock { $http = [System.Net.HttpListener]::new() $http.Prefixes.Add($using:prefix) $http.Start() $spriteTemplate = @" <div class="sprite"> <h2>__SPRITE_FILENAME__</h2> <div class="sprite-content"> <img src="images/__SPRITE_FILENAME__" alt="__SPRITE_FILENAME__" /> </div> </div> "@ try { while ($http.IsListening) { $contextTask = $http.GetContextAsync() while (-not $contextTask.AsyncWaitHandle.WaitOne(200)) { } $context = $contextTask.GetAwaiter().GetResult() Write-Host "Starting request $($context.Request.HttpMethod) $($context.Request.RawUrl)" if ($context.Request.HttpMethod -eq 'GET' -and $context.Request.RawUrl -eq '/') { $sprites = Get-ChildItem "$using:contentRoot/Images/*.png" $template = Get-Content -Raw "$using:contentRoot/Private/index.html" if(!$sprites) { Write-Warning "No sprites found matching path '$using:contentRoot/Images/*.png'" } $spriteContent = "" foreach($sprite in $sprites) { $spriteContent += $spriteTemplate -replace "__SPRITE_FILENAME__", $sprite.Name } $template = $template -replace "__SPRITE_CONTENT__", $spriteContent $buffer = [System.Text.Encoding]::UTF8.GetBytes($template) $context.Response.ContentLength64 = $buffer.Length $context.Response.OutputStream.Write($buffer, 0, $buffer.Length) $context.Response.OutputStream.Close() Write-Host "Rendered index.html" continue } if ($context.Request.HttpMethod -eq 'GET' -and $context.Request.RawUrl -match '/images/[^.]+\.png') { $image = [System.IO.File]::ReadAllBytes("$using:contentRoot$($context.Request.RawUrl -replace '/images/', '/Images/')") $context.Response.ContentType = "image/png" $context.Response.ContentLength64 = $image.Length $context.Response.OutputStream.Write($image, 0, $image.Length) $context.Response.OutputStream.Close() Write-Host "Rendered $($context.Request.RawUrl)" continue } $notFound = "Not Found" $buffer = [System.Text.Encoding]::UTF8.GetBytes($notFound) $context.Response.StatusCode = "404" $context.Response.ContentLength64 = $buffer.Length $context.Response.OutputStream.Write($buffer, 0, $buffer.Length) $context.Response.OutputStream.Close() Write-Host "Not found: $($context.Request.RawUrl)" } } finally { $http.Stop() } } Write-Host -ForegroundColor Green "Web server is running at $prefix" Write-Host -ForegroundColor Green "Press Control-C to exit" try { Start-Process $prefix } catch { Write-Verbose "Could not open browser" } while($job.State -eq "Running") { Start-Sleep -Seconds 1 } } finally { Write-Host "Job log:" $job | Receive-Job $job | Stop-Job $job | Remove-Job } } |