What causes Write-Host colors to perform like this?

996 views Asked by At

I am currently playing with the colors in PS ISE. It is a few prompts in which some require only reading and some require user input. I realized that the colors seem to do their own after performing a clear and initializing new write-host commands with color.

I have provided the code for testing.

Any thoughts?

Running PS Script

After pressing 'Enter' on the screen above

function logo {
    Write-Host ("==" * 23) -ForegroundColor Red -BackgroundColor DarkRed
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host (" _________  _______   ________  _________   ") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("|\___   ___\\  ___ \ |\   ____\|\___   ___\ ") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("\|___ \  \_\ \   __/|\ \  \___|\|___ \  \_| ") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("     \ \  \ \ \  \_|/_\ \_____  \   \ \  \  ") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("      \ \  \ \ \  \_|\ \|____|\  \   \ \  \ ") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("       \ \__\ \ \_______\____\_\  \   \ \__\") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("        \|__|  \|_______|\_________\   \|__|") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed -NoNewLine
    Write-Host ("                        \|_________|        ") -ForegroundColor White -NoNewline
    Write-Host ("=") -ForegroundColor Red -BackgroundColor DarkRed

    Write-Host ("==" * 23) -ForegroundColor Red -BackgroundColor DarkRed
    Write-Host ("`n")
}

# - WARNING Read Host Confirmation
function warningConfirm() {
    param
    (
        [Parameter(Position = 0, ValueFromPipeline = $true)]
        [string]$msg,
        [string]$BackgroundColor = "White",
        [string]$ForegroundColor = "Red"
    )


    Write-Host -ForegroundColor $ForegroundColor -BackgroundColor $BackgroundColor -NoNewline $msg;
    return Read-Host
}

# - Read Host Confirmation
function confirm() {
    param
    (
        [Parameter(Position = 0, ValueFromPipeline = $true)]
        [string]$msg,
        [string]$BackgroundColor = "Yellow",
        [string]$ForegroundColor = "Black"

    )
    Write-Host -ForegroundColor $ForegroundColor -BackgroundColor $BackgroundColor -NoNewline $msg;
    return Read-Host
}

# - Text Colors
function text() {
    param
    (
        [Parameter(Position = 0, ValueFromPipeline = $true)]
        [string]$msg,
        [string]$BackgroundColor = "Yellow",
        [string]$ForegroundColor = "Black"
    )


    Write-Host -ForegroundColor $ForegroundColor -BackgroundColor $BackgroundColor -NoNewline $msg;
}
clear

logo
$continue = 0
while ( $continue -eq 0 ) {
    $opt = (Get-Host).PrivateData
    $opt.WarningBackgroundColor = "Red"
    $opt.WarningForegroundColor = "White"
    Write-Warning "This version of Test is for use on 2008R2 servers only."
    warningConfirm ("`nConfirm you are using the correct version by pressing 'Enter'")
    clear
    logo
    confirm ("`nTest is initiating procedures... To being processing Test jobs press > > Enter:")
    text ("Gathering information to run checks. . . `(Approx. 43 Jobs`)`n")
    $continue = 1  
}```


2

There are 2 answers

0
postanote On

Differences between the ISE and PowerShell console.

The ISE is really optimized for a dev environment, whereas the console host is run environment.

You cannot run the interactive executable in the ISE you can in the consolehost.

To prevent this, PowerShell ISE maintains a list of unsupported console applications and won’t run them. The list is stored in the variable $psUnsupportedConsoleApplications (which does not exist in the regular PowerShell console).

PowerShell ISE Limitations (Windows) | Microsoft Docs

PowerShell ISE Limitations

You cannot run interactive sessions in the ISE, so for example, you cannot run netsh or diskpart interactively. For a partial list of tools the ISE can’t run, type the following at the ISE prompt:

$psUnsupportedConsoleApplications # Results <# wmic wmic.exe cmd cmd.exe diskpart diskpart.exe edit.com netsh netsh.exe nslookup nslookup.exe powershell powershell.exe #>

In those situations, you should use the classic PowerShell console instead.

You can improve this list and add applications that you find won’t run well in PowerShell ISE. For example, you could add choice.exe to the list:

$psUnsupportedConsoleApplications.Add('choice.exe') choice.exe

choice.exe

Cannot start “choice.exe”. Interactive console applications are not supported. To run the application, use the Start-Process cmdlet or use “Start PowerShell.exe” from the File menu. To view/modify the list of blocked console applications, use

$psUnsupportedConsoleApplications

or consult online help.

To execute your exe, from the ISE script pane or ISE console, you have to do something like this…

$ConsoleCommand = 'whatever exe you want to use and all its params / switches'
{Start-Process powershell -ArgumentList "-NoExit","-Command  & { $ConsoleCommand }" -Wait}

This shells out to the console host, runs the commands, waits so you can see results, then you can close and go back to the ISE.

I wrote a function I pulled together that I keep available for these exact scenarios. That way I call my function, pass it my external exe command string and it runs as expected.

You can run these exe's in the ISE, but you must pass them all they need.

PowerShell: Running Executables

0
Adam On

Solution: I found that Start-Sleep -Second 1 (between .5 -1 secs) after performing Clear-Host would provide the ISE console a sec to catch up and not shift the colors. It doesn't look as aestheically pleasing as using just the console of course, but it does prevent colors from shifting.