📄 tconsole.cpp
字号:
/*****************************************************************************/
/* TConsole.cpp Copyright (c) Ladislav Zezula 2003 */
/*---------------------------------------------------------------------------*/
/* Implementation of the console window */
/*---------------------------------------------------------------------------*/
/* Date Ver Who Comment */
/* -------- ---- --- ------- */
/* 02.06.03 1.00 Lad The first version of TConsole.cpp */
/*****************************************************************************/
#include "stdafx.h"
#include "resource.h"
#include "TConsole.h"
#define CONSOLE_STYLES (WS_POPUP | ES_MULTILINE | ES_AUTOHSCROLL | ES_AUTOVSCROLL | ES_LEFT | ES_WANTRETURN | WS_VSCROLL)
#define CONSOLE_EXSTYLES (0)
//-----------------------------------------------------------------------------
// Script function table
TCommandInfo TConsole::m_Commands[] =
{
{"open", "o", Open, 1, 2, IDS_HELP_OPEN},
{"new", "n", New, 1, 2, IDS_HELP_NEW},
{"add", "a", Add, 1, 7, IDS_HELP_ADD},
{"extract", "e", Extract, 2, 4, IDS_HELP_EXTRACT},
{"rename", "r", Rename, 3, 3, IDS_HELP_RENAME},
{"move", "m", Move, 3, 3, IDS_HELP_MOVE},
{"delete", "d", Delete, 2, 2, IDS_HELP_DELETE},
{"flush", "f", Flush, 1, 2, IDS_HELP_COMPACT},
{"compact", NULL, Flush, 1, 2, IDS_HELP_COMPACT},
// {"list", "l", List, 1, 3, 0},
{"close", "c", Close, 0, 0, IDS_HELP_CLOSE},
{"script", "s", Script, 1, 1, IDS_HELP_SCRIPT},
{"chdir", "cd", Chdir, 1, 1, IDS_HELP_CHDIR},
{"dir", NULL, Dir, 0, 1, IDS_HELP_DIR},
{"exit", "x", Exit, 0, 0, IDS_HELP_EXIT},
{"quit", NULL, Exit, 0, 0, IDS_HELP_EXIT},
{"help", "h", Help, 0, 1, IDS_HELP_HELP},
{NULL, NULL, NULL, 0, 0, 0}
};
//-----------------------------------------------------------------------------
// Constructor and destructor
TConsole::TConsole()
{
m_pfnOldWndProc = NULL;
m_szScriptName[0] = 0;
m_szCommand[0] = 0;
m_szSaveDir[0] = 0;
m_szLastMpq[0] = 0;
m_hBrush = NULL;
m_hFont = NULL;
m_hConsole = NULL;
m_hLastMpq = NULL;
m_bShowPrompt = TRUE;
m_nMaxLength = 0;
m_bEnablePaint = TRUE;
m_nStart = 0;
m_nState = stIdle;
m_nLevel = 0;
}
TConsole::~TConsole()
{
if(m_hConsole != NULL && IsWindow(m_hConsole))
{
::DestroyWindow(m_hConsole);
m_hConsole = NULL;
}
}
//-----------------------------------------------------------------------------
// Public functions
int TConsole::CreateConsoleWindow(HWND hParent, RECT & rect)
{
LOGFONT LogFont;
DWORD dwStyles = CONSOLE_STYLES;
int nError = ERROR_SUCCESS;
// Save the directory
GetCurrentDirectory(sizeof(m_szSaveDir)-1, m_szSaveDir);
// Create the font
m_hBrush = CreateSolidBrush(RGB(0, 0, 0));
if(nError == ERROR_SUCCESS)
{
// Include WS_CHILD if a parent was given
if(hParent != NULL)
dwStyles |= WS_CHILDWINDOW;
m_hConsole = CreateWindowEx(CONSOLE_EXSTYLES, "EDIT", "", CONSOLE_STYLES,
rect.left, rect.top, rect.right-rect.left, rect.bottom-rect.top,
hParent, NULL, GetModuleHandle(NULL), NULL);
if(m_hConsole == NULL)
nError = GetLastError();
}
// Create the window font, resize the window and show it.
if(nError == ERROR_SUCCESS)
{
// Crate the font
ZeroMemory(&LogFont, sizeof(LOGFONT));
LogFont.lfHeight = 12;
LogFont.lfWidth = 9;
LogFont.lfWeight = FW_NORMAL;
LogFont.lfCharSet = DEFAULT_CHARSET;
LoadString(AfxGetResourceHandle(), IDS_CONSOLEFONT, LogFont.lfFaceName, sizeof(LogFont.lfFaceName)-1);
if((m_hFont = CreateFontIndirect(&LogFont)) == NULL)
nError = GetLastError();
SetWindowLong(m_hConsole, GWL_USERDATA, (LONG)this);
m_pfnOldWndProc = (WNDPROC)SetWindowLong(m_hConsole, GWL_WNDPROC, (LONG)SubclassedWindowProc);
SendMessage(m_hConsole, WM_SETFONT, (WPARAM)m_hFont, 0);
m_nMaxLength = SendMessage(m_hConsole, EM_GETLIMITTEXT, 0, 0);
ShowWindow(m_hConsole, SW_SHOWNORMAL);
}
return nError;
}
int TConsole::RunConsoleMode()
{
printf(IDS_CONSOLE_COPYRIGHT);
printf(IDS_CONSOLE_HELPONEXIT);
ShowPrompt();
m_nState = stConsole;
return ERROR_SUCCESS;
}
int TConsole::RunCurrentCommand()
{
printf(IDS_CONSOLE_COPYRIGHT);
if(m_szCommand[0] == 0)
return ERROR_INVALID_PARAMETER;
ShowPrompt();
printf("%s\n", m_szCommand);
m_nState = stRunning;
PostMessage(m_hConsole, WM_RUNCOMMAND, 0, 0);
return ERROR_SUCCESS;
}
int TConsole::SetWorkDir(const char * szWorkDir)
{
int nError = ERROR_SUCCESS;
if(!SetCurrentDirectory(szWorkDir))
nError = GetLastError();
return nError;
}
int TConsole::printf(const char * fmt, ...)
{
va_list argList;
int result;
// printf using argList
va_start(argList, fmt);
result = _printf(fmt, argList);
va_end(argList);
return result;
}
int TConsole::printf(UINT nIDFmt, ...)
{
va_list argList;
char fmt[256];
int result;
// Load the string from resources
if(LoadString(AfxGetResourceHandle(), nIDFmt, fmt, sizeof(fmt)-1) == 0)
return 0;
// printf using argList
va_start(argList, nIDFmt);
result = _printf(fmt, argList);
va_end(argList);
return result;
}
void TConsole::ShowPrompt()
{
char szCurDir[MAX_PATH];
char * szSrc;
char * szTrg;
int nLength;
if(m_bShowPrompt)
{
GetCurrentDirectory(sizeof(szCurDir)-1, szCurDir);
nLength = strlen(szCurDir);
if(nLength > 32)
{
szTrg = szCurDir + 1;
if(*szTrg == ':')
szTrg++;
szTrg++;
szSrc = szCurDir + nLength - 28;
memmove(szTrg, szSrc, nLength - (szSrc - szCurDir));
}
printf("%s>", szCurDir);
}
SendMessage(m_hConsole, EM_GETSEL, (WPARAM)&m_nStart, (LPARAM)&m_nStart);
}
//-----------------------------------------------------------------------------
// Helper functions
int TConsole::ReadLine(FILE * fp, TCHAR * szBuffer, int nMaxChars)
{
_TINT ch = 0;
int count = 0;
*szBuffer = 0;
if(feof(fp))
return -1;
while(!feof(fp) && (ch = _fgettc(fp)) != (TCHAR)-1)
{
if(ch == _T('\n'))
break;
if(0 <= ch && ch <= _T(' ') && ch != _T('\t'))
ch = _T(' ');
*szBuffer++ = (TCHAR)ch;
if(++count == nMaxChars)
{
// Skip line
while(!feof(fp) && fgetc(fp) != _T('\n'));
*szBuffer = 0;
return -1; // Line is to long
}
}
*szBuffer = 0;
return count;
}
// Processes pending messages
int TConsole::ProcessMessages()
{
MSG msg;
while(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return ERROR_SUCCESS;
}
int TConsole::ExtractFile(HANDLE hMpq, const char * szToExtract, const char * szExtracted, LCID lcLocale)
{
HANDLE hLocalFile = INVALID_HANDLE_VALUE;
HANDLE hMpqFile = NULL;
int nError = ERROR_SUCCESS;
// Create the local file
if(nError == ERROR_SUCCESS)
{
hLocalFile = CreateFile(szExtracted, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL);
if(hLocalFile == INVALID_HANDLE_VALUE)
nError = GetLastError();
}
// Open the MPQ file
if(nError == ERROR_SUCCESS)
{
SFileSetLocale(lcLocale);
if(!SFileOpenFileEx(hMpq, szToExtract, 0, &hMpqFile))
nError = GetLastError();
}
// Copy the file's content
if(nError == ERROR_SUCCESS)
{
char szBuffer[0x1000];
DWORD dwTransferred = 1;
while(dwTransferred > 0)
{
SFileReadFile(hMpqFile, szBuffer, sizeof(szBuffer), &dwTransferred, NULL);
if(dwTransferred == 0)
break;
WriteFile(hLocalFile, szBuffer, dwTransferred, &dwTransferred, NULL);
if(dwTransferred == 0)
break;
}
}
// Close the files
if(hMpqFile != NULL)
SFileCloseFile(hMpqFile);
if(hLocalFile != INVALID_HANDLE_VALUE)
CloseHandle(hLocalFile);
return nError;
}
int TConsole::AddFiles(HANDLE hMpq, char * szToAdd, int nRelOffs)
{
WIN32_FIND_DATA wf;
HANDLE hFind = FindFirstFile(szToAdd, &wf);
char szFullPath[MAX_PATH];
char * szArchName = NULL;
char * szTemp;
DWORD dwQuality = 0; // Quality of Wave files
DWORD dwFlags = 0; // Flags for adding
BOOL bResult = TRUE;
int nFileType = 0;
int nError = ERROR_SUCCESS;
if(hFind == INVALID_HANDLE_VALUE)
printf(IDS_CONSOLE_FILENFOUND, szToAdd);
while(hFind != INVALID_HANDLE_VALUE && bResult)
{
// If a file found, add it to the archive
if((wf.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) == 0)
{
// Construct the archived name. Exclude created archive from the added files
GetFullPathName(wf.cFileName, sizeof(szFullPath), szFullPath, &szTemp);
if(stricmp(szFullPath, m_szLastMpq) && stricmp(szFullPath, m_szScriptName))
{
szArchName = szFullPath + nRelOffs;
while(*szArchName == '\\')
szArchName++;
// Get the file type
nFileType = GetAddFlagsByName(cfg.pAddFlags, cfg.nAddFlags, szArchName, dwFlags, dwQuality);
dwFlags |= MPQ_FILE_REPLACEEXISTING;
printf(IDS_CONSOLE_ADDINGFILE, szArchName);
if(nFileType == FILE_TYPE_DATA)
bResult = SFileAddFile(hMpq, szFullPath, szArchName, dwFlags);
if(nFileType == FILE_TYPE_WAVE)
bResult = SFileAddWave(hMpq, szFullPath, szArchName, dwFlags, dwQuality);
if(bResult == FALSE)
{
nError = GetLastError();
printf(IDS_CONSOLE_CANTADDFILE, szArchName, nError);
}
// Process pending messages
ProcessMessages();
}
}
bResult = FindNextFile(hFind, &wf);
}
if(hFind != INVALID_HANDLE_VALUE)
FindClose(hFind);
return ERROR_SUCCESS;
}
int TConsole::AddFolder(HANDLE hMpq, char * szFileMask, int nRelOffs)
{
WIN32_FIND_DATA wf;
HANDLE hFind = FindFirstFile("*", &wf);
BOOL bResult = TRUE;
int nError = ERROR_SUCCESS;
while(hFind != INVALID_HANDLE_VALUE && bResult)
{
if(wf.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
{
if(wf.cFileName[0] != '.')
{
if(SetCurrentDirectory(wf.cFileName))
{
nError = AddFolder(hMpq, szFileMask, nRelOffs);
SetCurrentDirectory("..");
}
else
{
nError = GetLastError();
printf(IDS_CONSOLE_CANTCD, wf.cFileName, nError);
}
}
}
bResult = FindNextFile(hFind, &wf);
}
if(hFind != INVALID_HANDLE_VALUE)
FindClose(hFind);
// Add the files within the folder
if(nError == ERROR_SUCCESS)
nError = AddFiles(hMpq, szFileMask, nRelOffs);
return nError;
}
int TConsole::CloseLastAccessedMpq()
{
if(m_hLastMpq != NULL)
SFileCloseArchive(m_hLastMpq);
m_hLastMpq = NULL;
m_szLastMpq[0] = 0;
return ERROR_SUCCESS;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -