TL;DR I wanted to draw graphs in powershell without any external dependancies. So I did, results below.
How to graph:
Create one or more array of points
Join arrays into another array of lines
Execute Draw-Graph function with some data
#Build graph [Array]$Line1 = 1..12 | ForEach-Object{Get-Random (10..20)} $p=Get-Random (14..25) $p%5 [Array]$Line2 = 1..12 | ForEach-Object{ If($p%5 -eq 0){ $p-=(get-random (1..3)) } Else{ $p+=(get-random (1..5)) } $p } [Array]$Lines = $Line1,$Line2 $Legend = "Line1 Header","Line2 Header" $Colors = "Blue","Green" $file = ([guid]::NewGuid()).Guid $file = "$env:TEMP\$file.png" Draw-Graph -Lines $Lines -Legend $Legend -Colors $Colors -Header "Header" -SaveDestination $file .$file
Graph functions/Initialization
Add-Type -AssemblyName System.Windows.Forms,System.Drawing Function Get-Color{ $rbg = @() For($i = 0;$i -le 3;$i++){ Switch($i){ #Black 0{ $rbg += 255}#Get-Random -Minimum 128 -Maximum 255 } #RGB Default{$rbg += Get-Random -Minimum 0 -Maximum 255} } } Return $rbg } Function Draw-Graph{ Param( $Width = 1024, $Height = 512, [Array]$Lines, [Array]$Legend, [Array]$Colors, $Header = "Graph", $SaveDestination, [Switch]$Preview ) Begin{} Process{ If($Preview){ [Windows.Forms.Form]$Window = New-Object System.Windows.Forms.Form $Window.Width = $Width $Window.Height = $Height $Window.Show() $Window.Refresh() [Drawing.Graphics]$Graph = $Window.CreateGraphics() } Else{ $bmp = New-Object Drawing.Bitmap $Width,$Height $Graph = [Drawing.Graphics]::FromImage($bmp) } $Graph.InterpolationMode = [Drawing.Drawing2D.InterpolationMode]::HighQualityBicubic $Graph.SmoothingMode = [Drawing.Drawing2D.SmoothingMode]::AntiAlias $Graph.TextRenderingHint = [Drawing.Text.TextRenderingHint]::AntiAlias $Graph.CompositingQuality = [Drawing.Drawing2D.CompositingQuality]::HighQuality $Background = [System.Drawing.Color]::Snow $Graph.Clear($Background) $TextBrush = New-Object Drawing.SolidBrush([System.Drawing.Color]::FromArgb(255, 0, 212,252)) $Font = New-object System.Drawing.Font("arial",12) $gridPen = [Drawing.Pens]::LightGray #Draw Graph area $DrawArea = New-Object 'object[,]' 2,2 # X (Width) [int]$DrawArea[0,0] = $Width/10 [int]$DrawArea[0,1] = ($Width-$Width/6) # Y (Height) [int]$DrawArea[1,0] = $Height/10 [int]$DrawArea[1,1] = ($Height-$Height/3) # Get X bounds $xFac = ($Lines | ForEach-Object{$_.Length} | Sort -Descending)[0]-1 $xInc = ($DrawArea[0,1]-$DrawArea[0,0]+$DrawArea[0,0])/$xFac #Get Y bounds $yMax = ($lines | ForEach-Object{$_} | sort -Descending)[0] $yFac = ($DrawArea[1,1]-$DrawArea[1,0])/$yMax #Draw box $Graph.DrawRectangle($gridPen, ($DrawArea[0,0]),($DrawArea[1,0]),($DrawArea[0,1]),($DrawArea[1,1])) #Draw Header $Textpoint = New-Object System.Drawing.PointF ((($DrawArea[0,1]-$DrawArea[0,0])/2+$DrawArea[0,0]),($DrawArea[1,0]/2)) $Graph.DrawString($Header,$Font,$TextBrush,$TextPoint) #Draw horizontal lines $scaleFac = 0.1 $i = 1 #Get scale While($i -ge 1){ $scaleFac = $scaleFac*10 $i = $yMax/$scaleFac } $scaleFac = $scaleFac/10 0..($yMax/$scaleFac) | ForEach-Object{ $y = $DrawArea[1,1]-(($_*$scaleFac)*$yFac)+$DrawArea[1,0] $x1 = $DrawArea[0,0] $x2 = $DrawArea[0,1]+$DrawArea[0,0] $Graph.DrawLine($gridPen,$x1,$y,$x2,$y) $thisPoint = New-Object System.Drawing.PointF (($x1-10),($y-15)) $thisSF = New-object System.Drawing.StringFormat $thisSF.Alignment = "Far" $Graph.DrawString("$($_*$scaleFac)",$Font,$TextBrush,$thisPoint,$thisSF) } If($lines[0].Count -le 1){ $tmp = $Lines Remove-Variable Lines $Lines = @(0) $Lines[0] = $tmp Remove-Variable tmp $Lines } #DRAW LINE $l = 0 Foreach($Line in $Lines){ If($Colors.Count -gt $l){ $Pen = New-Object Drawing.Pen($Colors[$l]) } Else{ $rgb = Get-Color $Pen = New-object Drawing.Pen([System.Drawing.Color]::FromArgb($rgb[0],$rgb[1],$rgb[2],$rgb[3])) } $Pen.Width = 2 #Initiate/Reset Points $Points = @() $Step = 0 Foreach($point in $line){ $x = ($xInc*$step)+$DrawArea[0,0] $y = $DrawArea[1,1]-($point*$yFac)+$DrawArea[1,0] $Points += New-Object System.Drawing.PointF($x,$y) $Step++ } $Graph.DrawLines($pen,$Points) If($Legend.Count -gt $l){ $thisLegend = $Legend[$l] If($Colors.Count -gt $l){ $thisBrush = New-Object Drawing.SolidBrush($Colors[$l]) } Else{ $rgb = Get-Color $thisBrush = New-Object Drawing.SolidBrush([System.Drawing.Color]::FromArgb($rgb[0],$rgb[1],$rgb[2],$rgb[3])) } $y = $DrawArea[1,1]+$DrawArea[1,0]+20 $x = $DrawArea[0,0]+100*$l $thisPoint = New-Object System.Drawing.PointF ($x,$y) $thisFont = New-Object System.Drawing.Font("arial",12,[System.Drawing.FontStyle]::Bold) $Graph.DrawString($thisLegend,$thisFont,$thisBrush,$thisPoint) } $l++ } } End{ If($Preview){ Start-Sleep 10 } Else{ $bmp.save($SaveDestination) } Try{$Graph.Dispose()}Catch{} Try{$bmp.Dispose()}Catch{} Try{$Window.Close()}Catch{} Try{$Window.Dispose()}Catch{} } }