Play-/Source/win32ui/VFSManagerWnd.cpp
jpd002 14129468e4 Removed uses of CList, CEvent, CEventEx, CEventHandler.
Fixed TR1 compilance.
Input configuration support for Win32.
Support for analog axis in PadMan.

git-svn-id: http://svn.purei.org/purei/trunk@361 b36208d7-6611-0410-8bec-b1987f11c4a2
2008-08-24 21:28:42 +00:00

408 lines
11 KiB
C++

#include <shlobj.h>
#include <stdio.h>
#include "VFSManagerWnd.h"
#include "layout/LayoutEngine.h"
#include "layout/LayoutStretch.h"
#include "layout/HorizontalLayout.h"
#include "win32/LayoutWindow.h"
#include "win32/Static.h"
#include "PtrMacro.h"
#include "../AppConfig.h"
#include "CdromSelectionWnd.h"
#include "string_cast.h"
#define CLSNAME _T("VFSManagerWnd")
#define WNDSTYLE (WS_CAPTION | WS_POPUP | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_SYSMENU)
#define WNDSTYLEEX (WS_EX_DLGMODALFRAME)
#define CDROM0PATH "ps2.cdrom0.path"
using namespace Framework;
using namespace std;
CVFSManagerWnd::CVFSManagerWnd(HWND hParent) :
CModalWindow(hParent)
{
RECT rc;
if(!DoesWindowClassExist(CLSNAME))
{
WNDCLASSEX w;
memset(&w, 0, sizeof(WNDCLASSEX));
w.cbSize = sizeof(WNDCLASSEX);
w.lpfnWndProc = CWindow::WndProc;
w.lpszClassName = CLSNAME;
w.hbrBackground = (HBRUSH)GetSysColorBrush(COLOR_BTNFACE);
w.hInstance = GetModuleHandle(NULL);
w.hCursor = LoadCursor(NULL, IDC_ARROW);
w.style = CS_HREDRAW | CS_VREDRAW;
RegisterClassEx(&w);
}
SetRect(&rc, 0, 0, 400, 250);
Create(WNDSTYLEEX, CLSNAME, _T("Virtual File System Manager"), WNDSTYLE, &rc, hParent, NULL);
SetClassPtr();
SetRect(&rc, 0, 0, 1, 1);
m_pList = new Win32::CListView(m_hWnd, &rc, LVS_REPORT | LVS_SORTASCENDING);
m_pList->SetExtendedListViewStyle(m_pList->GetExtendedListViewStyle() | LVS_EX_FULLROWSELECT);
m_pOk = new Win32::CButton(_T("OK"), m_hWnd, &rc);
m_pCancel = new Win32::CButton(_T("Cancel"), m_hWnd, &rc);
m_pLayout =
VerticalLayoutContainer(
LayoutExpression(Win32::CLayoutWindow::CreateCustomBehavior(1, 1, 1, 1, m_pList)) +
LayoutExpression(Win32::CLayoutWindow::CreateTextBoxBehavior(100, 40, new Win32::CStatic(m_hWnd, _T("Warning: Changing file system bindings while a program is running might be dangerous. Changes to 'cdrom0' bindings will take effect next time you load an executable."), SS_LEFT))) +
HorizontalLayoutContainer(
LayoutExpression(CLayoutStretch::Create()) +
LayoutExpression(Win32::CLayoutWindow::CreateButtonBehavior(100, 23, m_pOk)) +
LayoutExpression(Win32::CLayoutWindow::CreateButtonBehavior(100, 23, m_pCancel))
)
);
RefreshLayout();
m_devices[0] = new CDirectoryDevice("mc0", "ps2.mc0.directory");
m_devices[1] = new CDirectoryDevice("mc1", "ps2.mc1.directory");
m_devices[2] = new CDirectoryDevice("host", "ps2.host.directory");
m_devices[3] = new CCdrom0Device();
CreateListColumns();
UpdateList();
}
CVFSManagerWnd::~CVFSManagerWnd()
{
for(DeviceList::const_iterator deviceIterator(m_devices.begin());
m_devices.end() != deviceIterator; deviceIterator++)
{
delete deviceIterator->second;
}
}
long CVFSManagerWnd::OnCommand(unsigned short nID, unsigned short nCmd, HWND hSender)
{
if(hSender == m_pOk->m_hWnd)
{
Save();
Destroy();
return TRUE;
}
else if(hSender == m_pCancel->m_hWnd)
{
Destroy();
return TRUE;
}
return FALSE;
}
long CVFSManagerWnd::OnNotify(WPARAM wParam, NMHDR* pHDR)
{
if(pHDR->hwndFrom == m_pList->m_hWnd)
{
switch(pHDR->code)
{
case NM_DBLCLK:
int nSel = m_pList->GetSelection();
if(nSel != -1)
{
DeviceList::const_iterator deviceIterator(m_devices.find(m_pList->GetItemData(nSel)));
if(deviceIterator != m_devices.end())
{
CDevice* pDevice(deviceIterator->second);
if(pDevice->RequestModification(m_hWnd))
{
UpdateList();
}
}
}
break;
}
}
return FALSE;
}
void CVFSManagerWnd::RefreshLayout()
{
RECT rc;
GetClientRect(&rc);
SetRect(&rc, rc.left + 10, rc.top + 10, rc.right - 10, rc.bottom - 10);
m_pLayout->SetRect(rc.left, rc.top, rc.right, rc.bottom);
m_pLayout->RefreshGeometry();
Redraw();
}
void CVFSManagerWnd::CreateListColumns()
{
LVCOLUMN col;
RECT rc;
m_pList->GetClientRect(&rc);
memset(&col, 0, sizeof(LVCOLUMN));
col.pszText = _T("Device");
col.mask = LVCF_TEXT | LVCF_WIDTH;
col.cx = rc.right / 4;
m_pList->InsertColumn(0, &col);
memset(&col, 0, sizeof(LVCOLUMN));
col.pszText = _T("Binding Type");
col.mask = LVCF_TEXT | LVCF_WIDTH;
col.cx = rc.right / 4;
m_pList->InsertColumn(1, &col);
memset(&col, 0, sizeof(LVCOLUMN));
col.pszText = _T("Binding Value");
col.mask = LVCF_TEXT | LVCF_WIDTH;
col.cx = rc.right / 2;
m_pList->InsertColumn(2, &col);
}
void CVFSManagerWnd::UpdateList()
{
for(DeviceList::const_iterator deviceIterator(m_devices.begin());
m_devices.end() != deviceIterator; deviceIterator++)
{
CDevice* pDevice = deviceIterator->second;
unsigned int key = deviceIterator->first;
unsigned int index = m_pList->FindItemData(key);
if(index == -1)
{
tstring sDeviceName(string_cast<tstring>(pDevice->GetDeviceName()));
LVITEM itm;
memset(&itm, 0, sizeof(LVITEM));
itm.mask = LVIF_TEXT | LVIF_PARAM;
itm.pszText = const_cast<TCHAR*>(sDeviceName.c_str());
itm.lParam = key;
index = m_pList->InsertItem(&itm);
}
m_pList->SetItemText(index, 1, string_cast<tstring>(pDevice->GetBindingType()).c_str());
m_pList->SetItemText(index, 2, string_cast<tstring>(pDevice->GetBinding()).c_str());
}
}
void CVFSManagerWnd::Save()
{
for(DeviceList::const_iterator deviceIterator(m_devices.begin());
m_devices.end() != deviceIterator; deviceIterator++)
{
CDevice* pDevice = deviceIterator->second;
pDevice->Save();
}
}
///////////////////////////////////////////
//CDevice Implementation
///////////////////////////////////////////
CVFSManagerWnd::CDevice::~CDevice()
{
}
///////////////////////////////////////////
//CDirectoryDevice Implementation
///////////////////////////////////////////
CVFSManagerWnd::CDirectoryDevice::CDirectoryDevice(const char* sName, const char* sPreference)
{
m_sName = sName;
m_sPreference = sPreference;
m_sValue = CAppConfig::GetInstance().GetPreferenceString(m_sPreference);
}
CVFSManagerWnd::CDirectoryDevice::~CDirectoryDevice()
{
}
const char* CVFSManagerWnd::CDirectoryDevice::GetDeviceName()
{
return m_sName;
}
const char* CVFSManagerWnd::CDirectoryDevice::GetBindingType()
{
return "Directory";
}
const char* CVFSManagerWnd::CDirectoryDevice::GetBinding()
{
return m_sValue.c_str();
}
bool CVFSManagerWnd::CDirectoryDevice::RequestModification(HWND hParent)
{
BROWSEINFO bi;
LPITEMIDLIST item;
TCHAR sPath[MAX_PATH];
memset(&bi, 0, sizeof(BROWSEINFO));
bi.hwndOwner = hParent;
bi.lpszTitle = _T("Select new folder for device");
bi.ulFlags = BIF_RETURNONLYFSDIRS;
bi.lpfn = BrowseCallback;
bi.lParam = (LPARAM)this;
item = SHBrowseForFolder(&bi);
if(item == NULL)
{
return false;
}
if(SHGetPathFromIDList(item, sPath) == 0)
{
MessageBox(hParent, _T("Invalid directory."), NULL, 16);
CoTaskMemFree(item);
return false;
}
CoTaskMemFree(item);
m_sValue = string_cast<string>(sPath).c_str();
return true;
}
void CVFSManagerWnd::CDirectoryDevice::Save()
{
CAppConfig::GetInstance().SetPreferenceString(m_sPreference, m_sValue.c_str());
}
int CVFSManagerWnd::CDirectoryDevice::BrowseCallback(HWND hFrom, unsigned int nMsg, LPARAM lParam, LPARAM pData)
{
CDirectoryDevice* pDevice = reinterpret_cast<CDirectoryDevice*>(pData);
switch(nMsg)
{
case BFFM_INITIALIZED:
tstring sPath(string_cast<tstring>(pDevice->m_sValue.c_str()));
SendMessage(hFrom, BFFM_SETSELECTION, TRUE, reinterpret_cast<LPARAM>(sPath.c_str()));
break;
}
return 0;
}
///////////////////////////////////////////
//CCdrom0Device Implementation
///////////////////////////////////////////
CVFSManagerWnd::CCdrom0Device::CCdrom0Device()
{
const char* sPath;
char sDevicePath[32];
sPath = CAppConfig::GetInstance().GetPreferenceString(CDROM0PATH);
//Detect the binding type from the path format
if(!strcmp(sPath, ""))
{
m_nBindingType = CCdromSelectionWnd::BINDING_IMAGE;
m_sImagePath = "";
}
else if(strlen(sPath) == 6 && !strncmp(sPath, "\\\\.\\", 4))
{
sprintf(sDevicePath, "%c:\\", toupper(sPath[4]));
m_nBindingType = CCdromSelectionWnd::BINDING_PHYSICAL;
m_sDevicePath = sDevicePath;
}
else
{
m_nBindingType = CCdromSelectionWnd::BINDING_IMAGE;
m_sImagePath = sPath;
}
}
CVFSManagerWnd::CCdrom0Device::~CCdrom0Device()
{
}
const char* CVFSManagerWnd::CCdrom0Device::GetDeviceName()
{
return "cdrom0";
}
const char* CVFSManagerWnd::CCdrom0Device::GetBindingType()
{
if(m_nBindingType == CCdromSelectionWnd::BINDING_PHYSICAL)
{
return "Physical Device";
}
if(m_nBindingType == CCdromSelectionWnd::BINDING_IMAGE)
{
return "Disk Image";
}
return "";
}
const char* CVFSManagerWnd::CCdrom0Device::GetBinding()
{
if(m_nBindingType == CCdromSelectionWnd::BINDING_IMAGE)
{
if(m_sImagePath.length() == 0)
{
return "(None)";
}
else
{
return m_sImagePath.c_str();
}
}
if(m_nBindingType == CCdromSelectionWnd::BINDING_PHYSICAL)
{
return m_sDevicePath.c_str();
}
return "";
}
bool CVFSManagerWnd::CCdrom0Device::RequestModification(HWND hParent)
{
CCdromSelectionWnd::CDROMBINDING Binding;
char sDevicePath[32];
Binding.nType = (CCdromSelectionWnd::BINDINGTYPE)m_nBindingType;
Binding.sImagePath = m_sImagePath.c_str();
Binding.nPhysicalDevice = m_sDevicePath[0] - 'A';
CCdromSelectionWnd SelectionWnd(hParent, _T("Modify cdrom0 Binding"), &Binding);
SelectionWnd.DoModal();
if(!SelectionWnd.WasConfirmed()) return false;
SelectionWnd.GetBindingInfo(&Binding);
sprintf(sDevicePath, "%c:\\", Binding.nPhysicalDevice + 'A');
m_nBindingType = Binding.nType;
m_sImagePath = Binding.sImagePath;
m_sDevicePath = sDevicePath;
return true;
}
void CVFSManagerWnd::CCdrom0Device::Save()
{
if(m_nBindingType == CCdromSelectionWnd::BINDING_IMAGE)
{
CAppConfig::GetInstance().SetPreferenceString(CDROM0PATH, m_sImagePath.c_str());
}
if(m_nBindingType == CCdromSelectionWnd::BINDING_PHYSICAL)
{
char sDevicePath[32];
sprintf(sDevicePath, "\\\\.\\%c:", m_sDevicePath[0]);
CAppConfig::GetInstance().SetPreferenceString(CDROM0PATH, sDevicePath);
}
}