2006/01/10(Tue)タスクトレイアイコンモジュール

はてブ数 2006/01/10 17:15 プログラミング::HSP3 つーさ

タスクトレイにアイコンを格納します。そのまんまです。
アイコン付きバルーンメッセージなどにも対応です。

このモジュールはスクリプトに組み込んで自由に使用できます。

/* trayicon.hsp */
#module "trayicon"
;//   HSP3 で タスクトレイアイコンを作るモジュール 0.02 / 月影とも 2005. 8.12

;#define __TRAYICONSAMPLE__  ;// コメントを解除するとサンプルを実行できます

;// 追加命令説明
;//
;// CreateTrayIcon "ツールチップ文字列", アイコン番号, アイコンid
;//   トレイアイコンを作成する。
;//   ツールチップ文字列 = ツールチップに表示する63バイトまでの文字列。
;//   アイコン番号 = SetTrayIconFile で指定したファイルの中に含まれるアイコンのインデックスを指定。
;//   アイコンid   = 作成するiconのidを指定。複数アイコン作成時の識別用。
;//   作ったアイコンを弄られると、*onTrayIconEventというラベルに oncmd gosub でジャンプする。
;//   goto にしてしまうと、ウィンドウに次のメッセージがポストされるまで有効にならないっぽい?
;//
;// PopupBalloonTip "タイトル文字列","バルーンチップ本文", バルーンチップアイコン, アイコンid
;//   CreateTrayIcon済みのアイコンから、バルーンチップをポップアップさせる。
;//   タイトル文字列 = バルーンチップのタイトル部に表示する 63バイトまでの文字列。
;//   バルーンチップ本文 = バルーンチップの本文となる255バイトまでの文字列。
;//   バルーンチップアイコン = 0~3 が指定できますの。→ 0:ナシ 1:情報(i) 2:警告(!) 3:(エラー)X
;//   アイコンid = バルーンチップを表示させるアイコンのid
;//   Windows Me/2000/XP のみで有効、98SE以前では実行しても何も起こらなそう。
;//
;// DestroyTrayIcon アイコンid
;//   トレイアイコンを削除する。
;//
;// SetTrayIconFile "アイコンファイル.ico"
;//   使用するアイコンファイルを変更する。
;//   アイコンファイル = .ico とか .exe とか。
;//      "" にすると 自分自身のexeファイルアイコンを使う。
;// 

#define WM_TRAYEVENTSTART $900
#define MAXICONS 16 ;// ←アイコン最大数定義

;// 使用するAPIの定義。
#uselib "Kernel32.dll"
#func GetModuleFileName "GetModuleFileNameA" nullptr,prefstr,int ;// 自分自身の名前を得るAPI
#uselib "Shell32.dll"
#func ExtractIconEx "ExtractIconExA" sptr,int,nullptr,var,int ;// ファイルからアイコンを抽出する
#func Shell_NotifyIcon "Shell_NotifyIconA" int,var ;// タスクトレイアイコンを制御する
#uselib "user32.dll"
#func DestroyIcon "DestroyIcon" int ;// 抽出したアイコンを破棄する

#deffunc DestroyTrayIcon int iconid 
    dim NOTIFYICONDATA,88/4                                 ;// NOTIFYICONDATA 構造体を作る。
    NOTIFYICONDATA = 88, hWnd, iconid
    Shell_NotifyIcon 2, NOTIFYICONDATA                      ;// アイコンを削除する。
    if hIcon.iconid { DestroyIcon hIcon.iconid : hIcon.iconid = 0 } ;// アイコンハンドル破棄
return

#deffunc CreateTrayIcon str tooltip, int nIconIndex, int iconid
    if hIcon.iconid { DestroyTrayIcon iconid }              ;// すでに設定されていたら一度削除する
    ExtractIconEx icofile, nIconIndex, hIcon.iconid, 1      ;// ファイルからアイコンを取り出す。

    dim NOTIFYICONDATA,88/4                                 ;// NOTIFYICONDATA 構造体を作る。
    ;// ↓構造体のサイズ,ウィンドウハンドル,アイコンid,フラグ
    ;//                           メッセージID,アイコンハンドル,ツールチップ
    NOTIFYICONDATA = 88, hWnd_, iconid, 7, WM_TRAYEVENTSTART, hIcon.iconid
    poke NOTIFYICONDATA, 4*6, tooltip

    Shell_NotifyIcon 0, NOTIFYICONDATA                      ;// アイコンを登録する。

    ;// アイコンを弄られたらこのラベルにジャンプするよう指定する。
    oncmd gosub *onTrayIconEvent@, WM_TRAYEVENTSTART
return

#deffunc PopupBalloonTip str balloonInfoTitle, str balloonInfo, int balloonIcon,int iconid
    dim NOTIFYICONDATA,488/4
    NOTIFYICONDATA = 488, hWnd_, iconid, $10
    poke NOTIFYICONDATA, 4*40, balloonInfo
    NOTIFYICONDATA.104 = 1000* 20                           ;// タイムアウト時間: 20secで消える。
    poke NOTIFYICONDATA, 4*105, balloonInfoTitle
    NOTIFYICONDATA.121 = balloonIcon
    
    Shell_NotifyIcon 1, NOTIFYICONDATA                      ;// アイコンを変更する。
return

#deffunc SetTrayIconFile str filename 
    sdim icofile,1024
    if filename = "" { GetModuleFileName 1024 : icofile = refstr } 
    else { icofile = filename }
return 

#deffunc _init_trayicon_
    mref bmscr,96: hWnd_ = bmscr.13
    dim hIcon,MAXICONS : SetTrayIconFile "" : return
length
#deffunc _deinit_trayicon_ onexit ;// 終了時に全部のアイコンを削除。
    foreach hIcon : if hIcon.cnt { DestroyTrayIcon cnt } loop : return

#global
_init_trayicon_
;/// もじゅーるおわり ///

#ifdef __TRAYICONSAMPLE__@trayicon ;// こっからさんぷる

	CreateTrayIcon "さんぷるあいこん 0" ;// とりあえず作ってみる。
	PopupBalloonTip "ばるーん","これはバルーンチップのサンプルです。",3,0

	SetTrayIconFile "user32.dll"
	CreateTrayIcon "さんぷるあいこん 1",1,1
	CreateTrayIcon "さんぷるあいこん 2",4,2

	SetTrayIconFile "winmine.exe"
	CreateTrayIcon "さんぷるあいこん 3",0,3
	mes "トレイにアイコンを作りました。"
	stop
	

*onTrayIconEvent 
	;// コレと似たようなやつを、使う側で作ってしてください。
	;// この中で gotoをしてはイケマセン。必ず gosub で飛びましょう。
	;// stopもいけません、returnで必ずここに戻ってきましょう。
	iconid = wParam
	switch lparam
	    case $200 : swbreak ;// マウスがアイコンを触っただけ。
	    case $201 : mes "アイコン("+iconid+")で左ボタンが押されました" : swbreak
	    case $202 : mes "アイコン("+iconid+")で左ボタンが離されました" : swbreak
	    case $203 : mes "アイコン("+iconid+")で左ボタンがダブルクリックされました" : swbreak
	    case $204 : mes "アイコン("+iconid+")で右ボタンが押されました" : swbreak
	    case $205 : mes "アイコン("+iconid+")で右ボタンが離されました" : swbreak
	    case $206 : mes "アイコン("+iconid+")で右ボタンがダブルクリックされました" : swbreak
	    case $207 : mes "アイコン("+iconid+")で真ん中のボタンが押されました" : swbreak
	    case $208 : mes "アイコン("+iconid+")で真ん中のボタンが離されました" : swbreak
	    case $209 : mes "アイコン("+iconid+")で真ん中のボタンがダブルクリックされました" : swbreak
	swend
    return ;// リターンを忘れない。
#endif