// PlayFileDlg.h: interface and implementation of the CPlayFileDlg class.
//
/////////////////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#include <Shellapi.h> // Shell_NotifyIcon - note Shell32.dll is huge! > 8 Meg (XP)
#include "WndPlacement.h"
#include "EventManager.h"
#include "MacRcrdImport.h"
///////////////////////////////////////////////////////////////////////////////
#define WM_TRAYICONCLICK WM_USER+0x0701
#define REG_KEY_WINDOW _T("Software\\CodeAsm\\MacRcrd\\Window")
#define REG_KEY_LASTPOS _T("Position")
class CPlayFileDlg : public CDialogImpl<CPlayFileDlg>,
public CEventManager
{
public:
HICON m_hIcon;
bool m_bAutoPlay;
TCHAR m_szFileName[MAX_PATH];
public:
enum { IDD = IDD_MACRCRD_DLG };
CPlayFileDlg() : m_bAutoPlay(false), m_hIcon(0)
{
memset(m_szFileName,0,sizeof(m_szFileName));
}
virtual ~CPlayFileDlg()
{
}
void SetAutoPlay(bool bAutoPlay) { m_bAutoPlay = bAutoPlay; }
bool GetAutoPlay() { return m_bAutoPlay; }
void SetFileName(LPCTSTR szFileName) { lstrcpyn(m_szFileName, szFileName, MAX_PATH); }
BEGIN_MSG_MAP(CPlayFileDlg)
MESSAGE_HANDLER(WM_INITDIALOG, OnInitDialog)
COMMAND_HANDLER(IDC_BTN_RECORD, BN_CLICKED, OnRecordClicked)
COMMAND_HANDLER(IDC_BTN_PLAY, BN_CLICKED, OnPlayClicked)
COMMAND_HANDLER(IDC_BTN_BROWSE, BN_CLICKED, OnBrowseClicked)
COMMAND_HANDLER(IDOK, BN_CLICKED, OnOK)
MESSAGE_HANDLER(WM_SYSCOMMAND, OnSysCommand)
MESSAGE_HANDLER(WM_TRAYICONCLICK, OnTrayIconClick)
MESSAGE_HANDLER(WM_CANCELJOURNAL, OnCancelJournal)
MESSAGE_HANDLER(WM_CLOSE, OnClose)
MESSAGE_HANDLER(WM_DESTROY, OnDestroy)
END_MSG_MAP()
LRESULT OnInitDialog(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
// Show application on taskbar...
ModifyStyleEx(0, WS_EX_APPWINDOW);
// Set window icon
m_hIcon = LoadIcon(_Module.GetResourceInstance(), MAKEINTRESOURCE(IDI_MACRCRD));
SetIcon(m_hIcon, TRUE);
SetIcon(m_hIcon, FALSE);
// Initialize controls...
SetDlgItemText(IDC_TXT_EVENTFILE, m_szFileName);
SendDlgItemMessage(IDC_PLAY_LOOP_INC, UDM_SETRANGE32, (WPARAM)-1, (LPARAM)999);
// Get windowplacement if exists
CWindowPlacement wndPlacement;
HKEY hKey;
DWORD dwDisposition = 0;
if (ERROR_SUCCESS == RegCreateKeyEx(HKEY_CURRENT_USER, REG_KEY_WINDOW, 0, NULL, 0,
KEY_ALL_ACCESS, NULL, &hKey, &dwDisposition ))
{
if (wndPlacement.GetPosData(hKey, REG_KEY_LASTPOS))
wndPlacement.SetPosData( m_hWnd );
RegCloseKey( hKey );
}
// Auto play a file
if ( GetAutoPlay() )
{
PostMessage(WM_COMMAND, MAKEWPARAM(IDC_BTN_PLAY, BN_CLICKED), NULL);
}
return 0;
}
LRESULT OnRecordClicked(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled)
{
if (!IsRecording())
{
// Get file name...
GetDlgItemText(IDC_TXT_EVENTFILE, m_szFileName, MAX_PATH);
bool bSkipMouse = SendDlgItemMessage(IDC_REC_MOUSE, BM_GETSTATE, 0, 0) == BST_CHECKED;
bool bSkipKey = SendDlgItemMessage(IDC_REC_KEYBOARD, BM_GETSTATE, 0, 0) == BST_CHECKED;
HRESULT hr = InstallRecorder((LONG_PTR)EventCallback, (LONG_PTR)this, EVTOBJECT_FUNCTION);
if (SUCCEEDED(hr))
{
StartRecorder(bSkipMouse, bSkipKey);
SetDlgItemText(IDC_BTN_RECORD, _T("Stop"));
PostMessage(WM_SYSCOMMAND, SC_MINIMIZE, NULL);
if (WaitForCancelJournal() < 0)
{
// Just Exit...
UninstallRecorder();
PostQuitMessage( 0 );
}
}
}
else {
HRESULT hr = UninstallRecorder();
StopRecorder( false );
SetDlgItemText(IDC_BTN_RECORD, _T("Record"));
if (m_szFileName[0] != 0)
SaveEventFile( m_szFileName );
OnRestore();
}
return 0;
}
LRESULT OnPlayClicked(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled)
{
if (!IsPlaying())
{
// Get file name...
GetDlgItemText(IDC_TXT_EVENTFILE, m_szFileName, MAX_PATH);
bool bSkipMouse = SendDlgItemMessage(IDC_PLAY_MOUSE, BM_GETSTATE, 0, 0) == BST_CHECKED;
bool bSkipKey = SendDlgItemMessage(IDC_PLAY_KEYBOARD, BM_GETSTATE, 0, 0) == BST_CHECKED;
BOOL bTranslated = FALSE;
int nRepeat = (int) GetDlgItemInt(IDC_PLAY_LOOP, &bTranslated, TRUE);
if (LoadEventFile( m_szFileName ))
{
HRESULT hr = InstallPlayer((LONG_PTR)EventCallback, (LONG_PTR)this, EVTOBJECT_FUNCTION);
if (SUCCEEDED(hr))
{
StartPlayer( bSkipMouse, bSkipKey, nRepeat);
SetDlgItemText(IDC_BTN_PLAY, _T("Stop"));
PostMessage(WM_SYSCOMMAND, SC_MINIMIZE, NULL);
if (WaitForCancelJournal() < 0)
{
// Just Exit...
UninstallPlayer();
PostQuitMessage( 0 );
}
}
}
}
else {
HRESULT hr = UninstallPlayer();
StopPlayer();
SetDlgItemText(IDC_BTN_PLAY, _T("Play"));
OnRestore();
}
return 0;
}
LRESULT OnBrowseClicked(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled)
{
TCHAR szFile[MAX_PATH] = { 0 }; // buffer for file name
// Initialize OPENFILENAME
OPENFILENAME ofn = { 0 }; // common dialog box structure
ofn.lStructSize = sizeof(OPENFILENAME);
ofn.hwndOwner = m_hWnd;
ofn.lpstrFile = szFile;
ofn.nMaxFile = sizeof(szFile)/sizeof(TCHAR);
ofn.lpstrFilter = _T("Event File\0*.evr\0All Files\0*.*\0");
ofn.nFilterIndex = 1;
ofn.lpstrFileTitle = NULL;
ofn.nMaxFileTitle = 0;
ofn.lpstrInitialDir = NULL;
ofn.Flags = OFN_CREATEPROMPT|OFN_PATHMUSTEXIST|OFN_FILEMUSTEXIST;
ofn.Flags |= OFN_HIDEREADONLY |OFN_NONETWORKBUTTON;
// Display the Open dialog box.
if (GetOpenFileName(&ofn) != FALSE)
{
SetDlgItemText(IDC_TXT_EVENTFILE, ofn.lpstrFile);
}
return 0;
}
LRESULT OnOK(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled)
{
EndDialog(IDOK);
return 0;
}
LRESULT OnSysCommand(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
bHandled = FALSE;
if (wParam == SC_MINIMIZE)
{
OnMinimize();
bHandled = TRUE;
}
return 0;
}
LRESULT OnTrayIconClick(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
UINT uID = (UINT) wParam;
UINT uMouseMsg = (UINT) lParam;
if (uMouseMsg == WM_LBUTTONDOWN)
{
OnRestore();
}
return 0;
}
LRESULT OnCancelJournal(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
if (IsRecording())
PostMessage(WM_COMMAND, MAKEWPARAM(IDC_BTN_RECORD, BN_CLICKED), NULL);
if (IsPlaying())
PostMessage(WM_COMMAND, MAKEWPARAM(IDC_BTN_PLAY, BN_CLICKED), NULL);
return 0;
}
LRESULT OnClose(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
EndDialog(IDCANCEL);
return 0;
}
LRESULT OnDestroy(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
{
CWindowPlacement wndPlacement( m_hWnd );
HKEY hKey;
if (ERROR_SUCCESS == RegOpenKeyEx(HKEY_CURRENT_USER, REG_KEY_WINDOW, 0, KEY_WRITE, &hKey ))
{
wndPlacement.SetPosData(hKey, REG_KEY_LASTPOS);
RegCloseKey( hKey );
}
TrayIconConfig(_T(""), NULL, FALSE);
return 0;
}
///////////////////////////////////////////////////////////////////////////////
// TrayIconConfig
void TrayIconConfig(LPCTSTR szTip, HICON hIcon, BOOL bAddIcon)
{
NOTIFYICONDATA icondata;
memset(&icondata, 0, sizeof(icondata));
icondata.cbSize = sizeof(icondata);
icondata.uID = IDD_MACRCRD_DLG; // use the dialog id as the uID value
icondata.hWnd = m_hWnd;
icondata.hIcon = hIcon;
_tcscpy(icondata.szTip, szTip);
icondata.uCallbackMessage = WM_TRAYICONCLICK;
icondata.uFlags = NIF_ICON|NIF_MESSAGE|NIF_TIP;
::Shell_NotifyIcon((bAddIcon ? NIM_ADD : NIM_DELETE ), &icondata);
}
///////////////////////////////////////////////////////////////////////////////
// OnMinimize
void OnMinimize()
{
ShowWindow(SW_MINIMIZE);
TrayIconConfig(_T("Event Recorder"), m_hIcon, TRUE);
ShowWindow(SW_HIDE);
}
///////////////////////////////////////////////////////////////////////////////
// OnRestore
void OnRestore()
{
if (!IsWindowVisible())
{
ShowWindow(SW_SHOW);
}
ShowWindow(SW_RESTORE);
TrayIconConfig(_T("Event Recorder"), NULL, FALSE);
}
///////////////////////////////////////////////////////////////////////////////
// WaitForCancelJournal
int WaitForCancelJournal()
{
MSG msg = { 0 };
int nResult = 0;
while( (nResult = GetMessage( &msg, NULL, 0, 0 )) > 0)
{
if (msg.message != WM_CANCELJOURNAL)
{
TranslateMessage(&msg);
DispatchMessage(&msg);
// break if not in recording or playback
if (!IsRecording() && !IsPlaying())
break;
}
else
{
PostMessage(WM_CANCELJOURNAL, NULL, NULL);
MessageBeep(MB_ICONASTERISK);
break; // just exit
}
}
return nResult;
}
///////////////////////////////////////////////////////////////////////////////
// EventCallback
static LRESULT CALLBACK EventCallback(int nCode, WPARAM wParam, LPARAM lParam, LONG_PTR dwEventObjInstance)
{
LRESULT lRes = 0;
CPlayFileDlg* pThis = reinterpret_cast<CPlayFileDlg*>( dwEventObjInstance );
if (nCode != EVTMSG_STOPPED)
{
EventType event = static_cast<EventType>( (char)nCode );
if (pThis->IsRecording())
lRes = pThis->OnRecordEvent(event, lParam);
else if (pThis->IsPlaying())
lRes = pThis->OnPlayEvent(event, lParam);
}
if (lRes==-1 || nCode == EVTMSG_STOPPED) {
if (pThis->IsRecording())
::SendMessage(pThis->m_hWnd, WM_COMMAND, MAKEWPARAM(IDC_BTN_RECORD, BN_CLICKED), NULL);
else if (pThis->IsPlaying())
::SendMessage(pThis->m_hWnd, WM_COMMAND, MAKEWPARAM(IDC_BTN_PLAY, BN_CLICKED), NULL);
lRes = 0;
}
return lRes;
}
};