#include "stdafx.h"
#include "resource.h"
#include "FWatchApp.hpp"

#include <assert.h>

#include "TaskIcon.hpp"

CTaskIcon::CTaskIcon(HWND v_hWnd, UINT v_uID, UINT v_uMessageID, UINT v_hIconID, UINT v_uDefaultMessageID)
	: bCreated_(false)
	, hWnd_(v_hWnd)
	, uMessageID_(v_uMessageID)
	, uID_(v_uID)
	, uIconID_(v_hIconID)
	, uDefaultMessageId_(v_uDefaultMessageID)
{
}

void CTaskIcon::Create()
{
	if (! bCreated_) {
		ReCreate();
	}
}

void CTaskIcon::ReCreate()
{
	for (int retry = 0; retry < 10; retry++) {
		icondata_.cbSize = sizeof(NOTIFYICONDATA);
		icondata_.hWnd = hWnd_;
		icondata_.uID  = uID_;
		icondata_.uFlags = NIF_ICON | NIF_TIP | NIF_MESSAGE | NIM_SETFOCUS;
		icondata_.uCallbackMessage = uMessageID_;
		icondata_.hIcon = ::LoadIcon(app.getInstanceHandle(), MAKEINTRESOURCE(uIconID_));
		icondata_.uVersion = NOTIFYICON_VERSION;
		app.LoadString(uDefaultMessageId_, icondata_.szTip, sizeof(icondata_.szTip));
		::Shell_NotifyIcon(NIM_SETVERSION, &icondata_);
		if (::Shell_NotifyIcon(NIM_ADD, &icondata_)) {
			// 成功
			break;
		}
		DWORD err = GetLastError();
		if (err != ERROR_TIMEOUT) {
			// 失敗
			break;
		}
		Sleep(100);
	}
	
	bCreated_ = true;
}

CTaskIcon::~CTaskIcon()
{
	Destroy();
}

void CTaskIcon::Destroy()
{
	// タスクトレイからアイコン削除
	if (bCreated_) {
		::Shell_NotifyIcon(NIM_DELETE, &icondata_);
		bCreated_ = false;
	}
}

void CTaskIcon::SetFocusToTray()
{
	icondata_.cbSize = sizeof(NOTIFYICONDATA);
	icondata_.hWnd = hWnd_;
	icondata_.uID  = uID_;
	icondata_.uFlags = 0;
	::Shell_NotifyIcon(NIM_SETFOCUS, &icondata_);
}

void CTaskIcon::ShowMessage(LPCTSTR v_message)
{
	//required:
	assert(v_message != NULL && "チップにNULLは指定できません。");
	assert(lstrlen(v_message) < sizeof(icondata_.szTip) && "チップが長すぎます。");
	//do:
	_tcscpy_s(icondata_.szTip, sizeof(icondata_.szTip), v_message);
	::Shell_NotifyIcon(NIM_MODIFY, &icondata_);
}

void CTaskIcon::ShowDefault()
{
	app.LoadString(uDefaultMessageId_, icondata_.szTip, sizeof(icondata_.szTip));
	::Shell_NotifyIcon(NIM_MODIFY, &icondata_);
}

