📄 main.cpp
字号:
// Pass in some text, if there are any qoute chars it will change
// them to \". This is the only way the conditional parse will
// be able to figure out strings.
void EscapeQuote(const char *pszText, CString &strQuoted);
// Returns TRUE if this string passed it is a number.
BOOL IsVarNumber(const char *pszText);
void GetSocketError(CString &strError);
void Connect(const char *pszName, const char *pszAddress, const char *pszPort);
// Sends the text out the socket.
void SendText(const char *pszText, BOOL bAppendCR);
// Sets the focus back to the user input control.
void SetFocusUserInput();
// Determines the IP address of this machine.
void GetIPAddress();
// Creates a socket to listen for inbound calls.
void InitListenSocket();
void CloseListenSocket();
// Checks to see if there are any inbound calls waiting to be
// accepted. If so, handles connecting them.
void CheckForChatConnections();
// Checks all the connected chat sockets for text.
void CheckForChatText();
void ParseCommandLine(int nArgc, char *pszArgv[]);
// For reading and writing the INI file.
void WriteIniString(const char *pszSection, const char *pszEntry, const char *pszValue);
void WriteIniInt(const char *pszSection, const char *pszEntry, int nValue);
CString GetIniString(const char *pszSection, const char *pszEntry, const char *pszDefault);
int GetIniInt(const char *pszSection, const char *pszEntry, int nDefault);
// Gets the INI file settings.
void GetOptions();
//////////////////////////////////////////////////////////////
//
int main(int nArgc, char *pszArgv[])
{
// afxMemDF = allocMemDF | checkAlwaysMemDF;
if (nArgc > 1)
ParseCommandLine(nArgc, pszArgv);
CLogLine logBoot;
if (_bBootLog)
_bBootLog = logBoot.SetFile(BOOTLOG); // Turn off if it fails to create the file.
if (_bBootLog)
logBoot.LogIt("Initializing WinSock.");
if (!AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))
{
cputs("MFC Failed to initialize.\n");
return(1);
}
if (_bBootLog)
logBoot.LogIt("Creating console screens.");
if (!_screen.IsValid())
{
cputs("Error: Unable to get standard console output handle.\n\r");
return(1);
}
WORD wOriginalAttr = _screen.GetColor();
// Set the random seed.
srand( (unsigned)time( NULL ) );
WSADATA _wsaData;
if (!_bUsingModem)
{
// Start up winsock dll.
if (WSAStartup(MAKEWORD(1,1),&_wsaData) != 0)
{
cputs("WSAStartup Failed!\n\r");
getch();
return(2);
}
}
for (int i=0;i<10;i++)
_strGlobalVars[i].Empty();
// Create the hash table for the command list.
if (_bBootLog)
logBoot.LogIt("Creating hash table for commands.");
HashCommands();
if (_bBootLog)
logBoot.LogIt("Creating hash table for procedures.");
HashProcedures();
// Set the default configuration.
if (_bBootLog)
logBoot.LogIt("Reading configuration file 'Mud Master.ini'.");
GetOptions();
CheckTime();
if (_bBootLog)
logBoot.LogIt("Creating scroll back buffer.");
if (!_scrollBack.Init(_config.nScrollBack))
{
cputs("Unable to allocate the memory for the scrollback buffer.\n\r");
cputs("Reduce the number of lines to remember in the setup.\n\r");
WSACleanup();
return(4);
}
_scrollBack.SetColor(F_WHITE|B_RED);
if (_bBootLog)
logBoot.LogIt("Initializing console window.");
_terminal.Init();
if (_bBootLog)
logBoot.LogIt("Initializing input bar.");
_tiUserInput.Init(0,24,80,_colors.wInput,MAX_INPUT_LEN);
if (_bBootLog)
logBoot.LogIt("Initializing history buffer.");
_history.Init(_config.nHistory,MAX_INPUT_LEN+1);
// See if the status bar needs to be displayed.
if (_config.bStatusBar)
_statusBar.ShowBar(_config.nStatusBarPos);
_terminal.Gotoxy(0,9);
// MSP needs to defaul to off. It will get turned back on when
// a path is set.
_config.bMspOn = FALSE;
// Fills in the host name and ip address in _config for this
// computer.
if (_bBootLog)
logBoot.LogIt("Fetching local computer IP address.");
GetIPAddress();
if (_bBootLog)
{
CString strTemp;
strTemp.Format("IP Address: %s",(const char *)_config.strIPAddress);
logBoot.LogIt(strTemp);
}
// Create the socket to listen for calls. This function cannot
// be called before GetIPAddress() or there will be problems.
if (_bBootLog)
logBoot.LogIt("Initializing chat listen socket.");
InitListenSocket();
// Need to make sure this is initialized before the default
// command file is read in. If there are any /loadlib statements
// in the command file this buffer needs to exists.
if (_bBootLog)
logBoot.LogIt("Creating DLL return result buffer.");
_pszDLLResult = new char[DLL_RESULT_LEN+1];
// Load up the default command file.
if (!_config.strDefaultFile.IsEmpty())
{
if (_bBootLog)
logBoot.LogIt("Loading default command file.");
Read(_config.strDefaultFile);
}
_tiUserInput.SetFocus();
if (_bBootLog)
logBoot.LogIt("Creating speed walk buffer.");
_pWalkBuf = new char[INBUF_SIZE+1];
if (_bBootLog)
logBoot.LogIt("Creating chat buffer.");
_pChatBuf = new char[INBUF_SIZE+1];
if (_bBootLog)
logBoot.LogIt("Creating mud connection buffer.");
char *pInBuf = new char[INBUF_SIZE+1];
// For slowing down how often chat connections are looked for.
int nCheckChatConnect = CHATCONNECT_INTERVAL;
// How often text on the chat connections is checked.
int nCheckChatText = CHATCHECK_INTERVAL;
// How often to check for window messages.
int nWindowMessage = WINMESSAGE_INTERVAL;
// How often to check the time.
int nTimerInterval = TIMER_INTERVAL;
int nEventCount;
KEYBOARDCHAR kbch;
EVENT *pEvent;
MACRO *pMacro;
int nRecvLen;
CString strLine;
BOOL bDone = FALSE;
MSG msg;
CString strTemp;
while(!bDone)
{
if (_config.bWinMessages)
{
nWindowMessage--;
if (!nWindowMessage)
{
if (::PeekMessage(&msg,NULL,0,0,PM_REMOVE))
::DispatchMessage(&msg);
nWindowMessage = WINMESSAGE_INTERVAL;
}
}
if (_cbdSoundDone.bSoundDone)
_sound.SoundDone();
// Check for any inbound chat requests.
nCheckChatConnect--;
if (_bChatListenEnabled && !nCheckChatConnect && !_config.bDoNotDisturb)
{
CheckForChatConnections();
nCheckChatConnect = CHATCONNECT_INTERVAL;
}
else
if (nCheckChatConnect < 0) // When DND is on number can go less than 0.
nCheckChatConnect = CHATCONNECT_INTERVAL;
// Checks all of the connected chat sockets for text waiting.
nCheckChatText--;
if (!nCheckChatText)
{
CheckForChatText();
nCheckChatText = CHATCHECK_INTERVAL;
}
nTimerInterval--;
if (!nTimerInterval)
{
CheckTime();
nTimerInterval = TIMER_INTERVAL;
}
// Check the events. _nTimerID will be non-zero if SetTimer worked. If
// SetTimer failed then event just aren't going to work.
if (_config.bDoEvents && _bCheckEvents && _events.GetCount())
{
nEventCount = _events.GetCount();
pEvent = _events.GetFirst();
while(pEvent != NULL)
{
if (pEvent->bEnabled && _dwTime - pEvent->dwStarted >= pEvent->dwElapse)
{
pEvent->dwStarted = _dwTime;
_debugStack.Push(_events.GetFindIndex(),STACK_TYPE_EVENT);
HandleInput(pEvent->strEvent);
_debugStack.Pop();
// It is possible that the number of events was changed
// while handling the actions. If this is true is will
// cause problems with the First/Next loop. So, if the
// number of events changes, start back over at the top
// of the list.
if (_events.GetCount() != nEventCount)
{
nEventCount = _events.GetCount();
pEvent = _events.GetFirst();
continue;
}
}
pEvent = _events.GetNext();
}
_bCheckEvents = FALSE;
}
if (_bConnected)
{
if (_bUsingModem)
{
nRecvLen = _modem.Read(pInBuf,INBUF_SIZE);
if (nRecvLen == -1)
{
PrintMessage("Read error on com port.");
_bConnected = FALSE;
_modem.Close();
}
else
if (nRecvLen > 0)
{
pInBuf[nRecvLen] = '\x0';
CString strTemp(pInBuf);
_terminal.Print(pInBuf);
_tiUserInput.SetFocus();
}
}
else
{
nRecvLen = recv(_hActiveSocket,pInBuf,INBUF_SIZE,0);
if (nRecvLen == SOCKET_ERROR)
{
nRecvLen = WSAGetLastError();
if (nRecvLen != WSAEWOULDBLOCK)
{
PrintError();
PrintMessage("Connection Lost.");
_bConnected = FALSE;
closesocket(_hActiveSocket);
_notifyDisconnect.Notify();
}
}
else
if (nRecvLen > 0)
{
pInBuf[nRecvLen] = '\x0';
if (_notifyRaw.Notify(pInBuf))
continue;
_terminal.Print(pInBuf,nRecvLen);
_tiUserInput.SetFocus();
}
else
{
PrintMessage("Connection Lost.");
_bConnected = FALSE;
closesocket(_hActiveSocket);
_notifyDisconnect.Notify();
}
}
} // if (_bConnected)
if (_keyboard.GetKey(kbch))
{
pMacro = _macros.FindKeyByValue(kbch);
if (pMacro != NULL)
{
if (!_config.bEcho && !_bUsingModem)
{
_terminal.Print("\n");
_tiUserInput.SetFocus();
}
if (pMacro->bSend)
{
CString strText(pMacro->strText);
_debugStack.Push(kbch.wKeyID,STACK_TYPE_MACRO);
HandleInput(strText);
_debugStack.Pop();
}
else
{
strLine = pMacro->strText.Left(pMacro->strText.GetLength()-1);
ReplaceVariables(strLine);
_tiUserInput.InsertText(strLine);
if (pMacro->bCR)
{
_tiUserInput.SetLineReady();
if (!_config.bEcho && !_bUsingModem)
{
_terminal.Print("\n");
_tiUserInput.SetFocus();
}
_tiUserInput.GetText(strLine);
_debugStack.Push(kbch.wKeyID,STACK_TYPE_MACRO);
HandleInput(strLine);
_debugStack.Pop();
}
}
continue;
}
if (_tiUserInput.IsProcessedKey(kbch))
{
_tiUserInput.ProcessKey(kbch);
if (_tiUserInput.IsLineReady())
{
_tiUserInput.GetText(strLine);
if (strLine != "!" && !strLine.IsEmpty())
{
// Only had to history buffer if it is not the
// same as the last line entered. Always add
// the line to the !.
if (_strLastLine != strLine)
_history.Add(strLine);
else
_history.SetAtBottom();
_strLastLine = strLine;
}
if (_notifyInput.Notify(strLine))
continue;
if (!_config.bEcho && !_bUsingModem)
{
_terminal.Print("\n");
_tiUserInput.SetFocus();
}
HandleInput(strLine);
}
continue;
}
if (kbch.bSpecial && kbch.bEnhanced)
{
if (!kbch.bAlt && !kbch.bShift && !kbch.bControl)
{
switch(kbch.wKeyCode)
{
case VK_UP : // Up-Arrow
if (_history.GetPrev(strLine))
_tiUserInput.SetText(strLine);
break;
case VK_DOWN : // Down-arrow
if (_history.GetNext(strLine))
_tiUserInput.SetText(strLine);
else
_tiUserInput.SetText("");
break;
} // switch(kbch.wKeyCode)
continue;
} // if (!kbch.bAlt && !kbch.bShift && !kbch.bControl)
if (kbch.bAlt && !kbch.bShift && !kbch.bControl)
{
switch(kbch.wKeyCode)
{
case VK_UP : // Alt Up Arrow
_scrollBack.DoIt();
break;
}
continue;
} // if (kbch.bAlt && !kbch.bShift && !kbch.bControl)
} // if (kbch.bSpecial)
switch(kbch.chKey)
{
case 0x18 : // Ctrl-X
bDone = TRUE;
continue;
}
} // if (_keyboard.GetKey(kbch))
} // while(!bDone)
if (_cti.pszTextToPrint)
delete [] _cti.pszTextToPrint;
delete [] pInBuf;
delete [] _pChatBuf;
delete [] _pWalkBuf;
delete [] _pszDLLResult;
// Clean up the midi if we are still playing.
if (_bMidiOpen)
mciSendString("close MudMaster", NULL, NULL, NULL);
// Get rid of the socket used for chat connections.
if (_hListenSocket != INVALID_SOCKET)
closesocket(_hListenSocket);
if (!_bUsingModem)
{
closesocket(_hActiveSocket);
WSACleanup();
}
COORD c;
c.X = 80;
c.Y = 25;
SetConsoleScreenBufferSize(_screen.m_hScreen,c);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -