functions/Add-Border.ps1
|
#add a border around a string of text <# originally published at https://gist.github.com/jdhitsolutions/0bbd6b64c107d7da23e65359c4d0e25c #> Function Add-Border { [CmdletBinding(DefaultParameterSetName = "single")] [alias('ab')] [OutputType([System.String])] Param( # The string of text to process [Parameter( Position = 0, Mandatory, ValueFromPipeline, ParameterSetName = 'single' )] [ValidateNotNullOrEmpty()] [string]$Text, [Parameter( Position = 0, Mandatory, ParameterSetName = 'block' )] [ValidateNotNullOrEmpty()] [Alias("tb")] [string[]]$textBlock, # The character to use for the border. It must be a single character. [ValidateNotNullOrEmpty()] [alias("border")] [string]$Character = "*", # add blank lines before and after text [Switch]$InsertBlanks, # insert X number of tabs [int]$Tab = 0, [Parameter(HelpMessage = "Enter an ANSI escape sequence to color the border characters." )] [string]$ANSIBorder, [Parameter(HelpMessage = "Enter an ANSI escape sequence to color the text." )] [string]$ANSIText ) Begin { Write-Verbose "Starting $($MyInvocation.MyCommand)" Write-Verbose "Running under PowerShell version $($PSVersionTable.PSVersion)" $tabs = "`t" * $tab Write-Verbose "Using a tab of $tab" Write-Verbose "Using border character $Character" $ansiClear = "$([char]0x1b)[0m" if ($PSBoundParameters.ContainsKey("ANSIBorder")) { Write-Verbose "Using an ANSI border Color" $Character = "{0}{1}{2}" -f $PSBoundParameters.ANSIBorder, $Character, $ansiClear } #define regex expressions to detect ANSI escapes. Need to subtract their #length from the string if used. Issue #79 [regex]$ansiOpen = "$([char]0x1b)\[\d+[\d;]+m" [regex]$ansiEnd = "$([char]0x1b)\[0m" } #begin Process { if ($PSCmdlet.ParameterSetName -eq 'single') { Write-Verbose "Processing '$text'" #get length of text $adjust = 0 if ($ansiOpen.IsMatch($text)) { $adjust += ($ansiOpen.matches($text) | Measure-Object length -sum).sum $adjust += ($ansiEnd.matches($text) | Measure-Object length -sum).sum Write-Verbose "Adjusting text length by $adjust." } $len = $text.Length - $adjust if ($PSBoundParameters.ContainsKey("ANSIText")) { Write-Verbose "Using an ANSIText color" $text = "{0}{1}{2}" -f $PSBoundParameters.ANSIText, $text, $AnsiClear } } else { Write-Verbose "Processing text block" #test if text block is already using ANSI if ($ansiOpen.IsMatch($textBlock)) { Write-Verbose "Text block contains ANSI sequences" $txtArray | ForEach-Object -begin {$tempLen = @()} -process { $adjust = 0 $adjust += ($ansiOpen.matches($_) | Measure-Object length -sum).sum $adjust += ($ansiEnd.matches($_) | Measure-Object length -sum).sum Write-Verbose "Length detected as $($_.length)" Write-Verbose "Adding adjustment $adjust" $tempLen += $_.length - $adjust } $len = $tempLen | Sort-Object -Descending | Select-Object -first 1 } elseif ($PSBoundParameters.ContainsKey("ANSIText")) { Write-Verbose "Using ANSIText for the block" $txtArray = $textBlock.split("`n").Trim() | ForEach-Object {"{0}{1}{2}" -f $PSBoundParameters.ANSIText, $_, $AnsiClear} $len = ($txtArray | Sort-Object -property length -Descending | Select-Object -first 1 -expandProperty length) - ($PSBoundParameters.ANSIText.length + 4) } else { Write-Verbose "Processing simple text block" $txtArray = $textBlock.split("`n").Trim() $len = $txtArray | Sort-Object -property length -Descending | Select-Object -first 1 -expandProperty length } Write-Verbose "Added $($txtArray.count) text block elements" } Write-Verbose "Using a length of $len" #define a horizontal line $hzLine = $Character * ($len + 4) if ($PSCmdlet.ParameterSetName -eq 'single') { Write-Verbose "Defining Single body" $body = "$tabs$Character $text $Character" } else { Write-Verbose "Defining textBlock body" [string[]]$body = $null foreach ($item in $txtArray) { if ($item) { Write-Verbose "$item [$($item.length)]" } else { Write-Verbose "detected blank line" } if ($ansiOpen.IsMatch($item)) { $adjust = $len $adjust += ($ansiOpen.matches($item) | Measure-Object length -sum).sum $adjust += ($ansiEnd.matches($item) | Measure-Object length -sum).sum Write-Verbose "Adjusting length to $adjust" $body += "$tabs$Character $(($item).PadRight($adjust)) $Character`r" } elseif ($PSBoundParameters.ContainsKey("ANSIText")) { #adjust the padding length to take the ANSI value into account $adjust = $len + ($PSBoundParameters.ANSIText.length + 4) Write-Verbose "Adjusting length to $adjust" $body += "$tabs$Character $(($item).PadRight($adjust)) $Character`r" } else { $body += "$tabs$Character $(($item).PadRight($len)) $Character`r" } } #foreach item in txtArray } Write-Verbose "Defining top border" [string[]]$out = "`n$tabs$hzLine" $lines = $body.split("`n") Write-Verbose "Adding $($lines.count) lines" | Write-Verbose if ($InsertBlanks) { Write-Verbose "Prepending blank line" $out += "$tabs$character $((" ")*$len) $character" } foreach ($item in $lines ) { $out += $item } if ($InsertBlanks) { Write-Verbose "Appending blank line" $out += "$tabs$character $((" ")*$len) $character" } Write-Verbose "Defining bottom border" $out += "$tabs$hzLine" #write the result to the pipeline $out } #process End { Write-Verbose "Ending $($MyInvocation.MyCommand)" } #end } #close function |