Advertisement:

Skystone Software

http://www.SkystoneSoftware.com

.NET Programming

NotifyIcon Balloons
Published: 8/18/2005

I answered a question about how to display a NotifyIcon balloon today on VBCity.com. The code is actually pretty simple if you don't mind messing around with Interop, here's a sample (taken from the Skystone.Shared.Win class library):

Imports System.Runtime.InteropServices 

Public Const WM_USER As Long = &H400 
Public Const NIF_MESSAGE As Int32 = &H1 
Public Const NIF_ICON As Int32 = &H2 
Public Const NIF_STATE As Int32 = &H8 
Public Const NIF_INFO As Int32 = &H10 
Public Const NIF_TIP As Int32 = &H4 
Public Const NIM_ADD As Int32 = &H0 
Public Const NIM_MODIFY As Int32 = &H1 
Public Const NIM_DELETE As Int32 = &H2 
Public Const NIM_SETVERSION As Int32 = &H4 
Public Const NOTIFYICON_VERSION As Int32 = &H5 
Public Const NIIF_ERROR As Int32 = &H3 
Public Const NIIF_INFO As Int32 = &H1 
Public Const NIIF_NONE As Int32 = &H0 
Public Const NIM_SETFOCUS As Int32 = &H3 
Public Const NIN_BALLOONSHOW As Long = (WM_USER + 2) 
Public Const NIN_BALLOONHIDE As Long = (WM_USER + 3) 
Public Const NIN_BALLOONTIMEOUT As Long = (WM_USER + 4) 
Public Const NIN_BALLOONUSERCLICK As Long = (WM_USER + 5) 

Public Enum BalloonMessageTypes 
	None = &H0 
	Info = &H1 
	[Error] = &H3 
End Enum 

<StructLayout(LayoutKind.Sequential)> _ 
Public Structure NOTIFYICONDATA 
	Public cbSize As Int32 
	Public hwnd As IntPtr 
	Public uID As Int32 
	Public uFlags As Int32 
	Public uCallbackMessage As IntPtr 
	Public hIcon As IntPtr 
	<MarshalAs(UnmanagedType.ByValTStr, SizeConst:=128)> _ 
	Public szTip As String 
	Public dwState As Int32 
	Public dwStateMask As Int32 
	<MarshalAs(UnmanagedType.ByValTStr, SizeConst:=256)> _ 
	Public szInfo As String 
	Public uTimeout As Int32 
	<MarshalAs(UnmanagedType.ByValTStr, SizeConst:=64)> _ 
	Public szInfoTitle As String 
	Public dwInfoFlags As Int32 
End Structure 

Public Declare Auto Function Shell_NotifyIconA Lib "shell32" (ByVal dwMessage As Integer, ByRef pnid As NOTIFYICONDATA) As Integer 

<Description("Displays a notification balloon associated with the specified NotifyIcon control.")> _ 
Public Shared Sub DisplayBalloon(ByRef NotifyIcon As System.Windows.Forms.NotifyIcon, ByVal BalloonTitle As String, _ 
		ByVal BalloonText As String, Optional ByVal MessageType As BalloonMessageTypes = BalloonMessageTypes.None) 
	Dim typNotifyIcon As Type = GetType(System.Windows.Forms.NotifyIcon) 
	Dim ptrWindow As IntPtr = (CType(typNotifyIcon.GetField("window", System.Reflection.BindingFlags.Instance Or _ 
		System.Reflection.BindingFlags.NonPublic).GetValue(NotifyIcon), System.Windows.Forms.NativeWindow)).Handle 
	Dim id As Int32 = CType(typNotifyIcon.GetField("id", System.Reflection.BindingFlags.Instance Or _ 
		System.Reflection.BindingFlags.NonPublic).GetValue(NotifyIcon), Integer) 
	Dim clsNID As NOTIFYICONDATA 
	With clsNID 
		.szTip = "" 
		.dwState = 0 
		.dwStateMask = 0 
		.hIcon = IntPtr.Zero 
		.uCallbackMessage = New IntPtr(&H200) 
		.uID = id 
		.hwnd = ptrWindow 
		.szInfo = BalloonText 
		.szInfoTitle = BalloonTitle 
		.uFlags = NIF_INFO 
		.cbSize = Marshal.SizeOf(clsNID) 
		.dwInfoFlags = CType(MessageType, Int32) 
		.uTimeout = NOTIFYICON_VERSION 
	End With 
	Dim result As Int32 = Shell_NotifyIconA(NIM_MODIFY, clsNID) 
End Sub 

<Description("Hides any notification balloon associated with the specified NotifyIcon control.")> _ 
Public Shared Sub HideBalloon(ByRef NotifyIcon As System.Windows.Forms.NotifyIcon) 
	Dim typNotifyIcon As Type = GetType(System.Windows.Forms.NotifyIcon) 
	Dim ptrWindow As IntPtr = (CType(typNotifyIcon.GetField("window", System.Reflection.BindingFlags.Instance Or _ 
		System.Reflection.BindingFlags.NonPublic).GetValue(NotifyIcon), System.Windows.Forms.NativeWindow)).Handle 
	Dim id As Int32 = CType(typNotifyIcon.GetField("id", System.Reflection.BindingFlags.Instance Or 		System.Reflection.BindingFlags.NonPublic).GetValue(NotifyIcon), Integer) 
	Dim clsNID As NOTIFYICONDATA 
		With clsNID 
		.szTip = "" 
		.dwState = 0 
		.dwStateMask = 0 
		.hIcon = IntPtr.Zero 
		.uCallbackMessage = New IntPtr(&H200) 
		.uID = id 
		.hwnd = ptrWindow 
		.szInfo = "" 
		.szInfoTitle = "" 
		.uFlags = NIF_INFO 
		.cbSize = Marshal.SizeOf(clsNID) 
		.dwInfoFlags = CType(BalloonMessageTypes.None, Int32) 
		.uTimeout = NOTIFYICON_VERSION 
	End With 
	Dim result As Int32 = Shell_NotifyIconA(NIM_MODIFY, clsNID) 
End Sub 
(NOTE: the result of the Shell_NotifyIcon call is captured for debugging purposes, but otherwise ignored).

Once shown, your application may want to respond to user-interaction with the bubble. To do so, you can subclass the NativeWindow class, and look for the special Notify Icon messages sent to the window:

<Description("Returns a class that will raise events related to the specified NotifyIcon balloon events.")> _
Public Shared Function HookBalloonEvents(ByVal NotifyIcon As System.Windows.Forms.NotifyIcon) As NotifyIconBubble
	Dim clsEvents As New NotifyIconBubble
	Dim typNotifyIcon As Type = GetType(System.Windows.Forms.NotifyIcon)
	Dim ptrWindow As IntPtr = (CType(typNotifyIcon.GetField("window", System.Reflection.BindingFlags.Instance _
		Or System.Reflection.BindingFlags.NonPublic).GetValue(NotifyIcon), System.Windows.Forms.NativeWindow)).Handle
	clsEvents.AssignHandle(ptrWindow)
	Return clsEvents
End Function

<Description("Defines a class that will raise events related to the specified NotifyIcon balloon events.")> _
Public Class NotifyIconBubble
	Inherits System.Windows.Forms.NativeWindow
	Public Event BallonHidden()
	Public Event BallonShown()
	Public Event BallonTimedOut()
	Public Event BallonClicked()
	Friend Sub New()
		'
	End Sub
	Protected Overrides Sub WndProc(ByRef m As System.Windows.Forms.Message)
	Select Case m.LParam.ToInt32
		Case NIN_BALLOONHIDE
			RaiseEvent BallonHidden()
		Case NIN_BALLOONSHOW
			RaiseEvent BallonShown()
		Case NIN_BALLOONTIMEOUT
			RaiseEvent BallonTimedOut()
		Case NIN_BALLOONUSERCLICK
			RaiseEvent BallonClicked()
		Case Else
	End Select
	MyBase.WndProc(m)
        End Sub
End Class

NOTE: This post has been elaborated on and turned into a FAQ on VBCity.com.



Written by Scott Waletzko for Skystone Software.
Copyright 2005-2007 by Echosoft Design Studios, LLC, All Rights Reserved.