Windows - Notify User with Balloon Tip Pop-up

Displays a balloon tip from the task tray for about 8 seconds for currently logged in user. Would invite anyone to help me get this code further! Worklet does use a custom icon file that I include as a file in the worklet.

#message
$msg = 'Hello world.'
$title = 'Company'
$icon = 'C:\Users\Public\Pictures\company.ico'
IF(!(Test-Path "$icon")){Copy-Item company.ico "$icon"}

# Build script that will send message. VBS is used to hide the PowerShell Script from popping up
$vbs = @"
command = "C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe -ExecutionPolicy Bypass -windowstyle hidden -File C:\ProgramData\Amagent\message.ps1 -Force"
 set shell = CreateObject("WScript.Shell")
 shell.Run command,0
"@
New-Item -Path "c:\ProgramData\Amagent" -Name "message.vbs" -ItemType "file" -Value $vbs -force

$script = @"
`$BalloonTipText = ("$msg")
`$BalloonTipTitle = "$title"
`$BalloonTipTime = 1000
`$BalloonTipIcon = 'None'

Add-Type -AssemblyName System.Windows.Forms
Add-Type -AssemblyName System.Drawing
[Windows.Forms.ToolTipIcon]`$BalloonTipIcon = `$BalloonTipIcon
`$ContextMenu = New-Object System.Windows.Forms.ContextMenu
`$MenuItem = New-Object System.Windows.Forms.MenuItem
        
`$NotifyIcon = New-Object Windows.Forms.NotifyIcon -Property @{
    BalloonTipIcon = `$BalloonTipIcon
    BalloonTipText = `$BalloonTipText
    BalloonTipTitle = `$BalloonTipTitle
    ContextMenu = `$ContextMenu
    Icon = "$icon"
    Text = -join `$BalloonTipText[0..62]
    Visible = `$false
}
`$NotifyIcon.contextMenu.MenuItems.AddRange(`$MenuItem)
`$NotifyIcon.Visible = `$True
`$MenuItem.Text = "Exit"
`$MenuItem.add_Click({
    `$NotifyIcon.Visible = `$true
    `$NotifyIcon.ShowInTaskbar = `$true
})
`$NotifyIcon.ShowBalloonTip(`$BalloonTipTime)
"@
New-Item -Path "c:\ProgramData\Amagent" -Name "message.ps1" -ItemType "file" -Value $script -force

# This will create a scheduled task
$SchedService = New-Object -ComObject Schedule.Service
$SchedService.Connect()
$Task = $SchedService.NewTask(0)
$Task.RegistrationInfo.Description = 'Balloon tip pop-up'
$Task.Settings.Enabled = $true
$Task.Settings.AllowDemandStart = $true
$trigger = $Task.triggers.Create(9)
$trigger.Enabled = $true
$action = $Task.Actions.Create(0)
$action.Path = 'C:\ProgramData\amagent\message.vbs'
$taskFolder = $SchedService.GetFolder('\')
$taskFolder.RegisterTaskDefinition('StartMsg', $Task , 6, 'Users', $null, 4)
Start-ScheduledTask -TaskName StartMsg

# Cleanup Scheduled Task and Script
Unregister-ScheduledTask -TaskName 'StartMsg' -Confirm:$false | Out-Null
Remove-Item -Path 'c:\ProgramData\Amagent\message.ps1' | Out-Null
Remove-Item -Path 'c:\ProgramData\Amagent\message.vbs' | Out-Null

Are you facing issues with this?

I’ve observed that it doesn’t always work when a user is connected over a terminal session. I think the issue may be in how the scheduled task is created to run as currently logged in user. Also have observed that on some systems it doesn’t execute at all, which may be related to execution policy. So I think there is room for improvement in those areas.

You might want to check if $currentusr is not null. Also, schedule task can be setup to run under the context of the local USERS group. That will work better.

2 Likes

Updated code above to run as the Users group. Huge thanks to this code by @jesumyip for helping me see how to get there with a COM object. Create scheduled task to run at user log-on as user him/herself

2 Likes