Files

617 lines
15 KiB
C++
Raw Permalink Normal View History

2026-03-03 13:56:44 +08:00
#include "StdAfx.h"
#include "TraceService.h" // #include "EventService.h"
#include <strsafe.h>
//////////////////////////////////////////////////////////////////////////
//<2F><>ɫ<EFBFBD><C9AB><EFBFBD><EFBFBD>
#define COLOR_TIME RGB(0,0,0)
#define COLOR_NORMAL RGB(125,125,125)
#define COLOR_WARN RGB(255,128,0)
#define COLOR_EXCEPTION RGB(200,0,0)
#define COLOR_DEBUG RGB(0,128,128)
#define IDM_MENU0 100
#define IDM_MENU1 110
#define IDM_MENU2 120
#define IDM_MENU3 130
#define IDM_MENU4 140
#define IDM_MENU5 150
#define TRACE_LEVEL_COUNT 5
//////////////////////////////////////////////////////////////////////////
struct tagTraceString
{
enTraceLevel enTL;
CString strMsg;
};
//׷<>ٷ<EFBFBD><D9B7><EFBFBD>
//////////////////////////////////////////////////////////////////////////
static ITraceService *g_pITraceService = NULL;
static bool g_bEnableTrace=true;
static CWHArray<tagTraceString *> g_aryTraceString;
static CWHArray<tagTraceString *> g_aryTraceStringStorage;
static CCriticalSection g_CS;
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD><EFBFBD><ECBAAF>
CTraceService::CTraceService()
{
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD>÷<EFBFBD><C3B7><EFBFBD>
bool CTraceService::SetTraceService(IUnknownEx * pIUnknownEx)
{
g_pITraceService = QUERY_OBJECT_PTR_INTERFACE(pIUnknownEx, ITraceService);
return NULL != g_pITraceService;
}
//<2F><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>
VOID * CTraceService::GetTraceService(const IID & Guid, DWORD dwQueryVer)
{
ASSERT(g_pITraceService);
if (g_pITraceService) return NULL;
return (VOID*)g_pITraceService->QueryInterface(Guid, dwQueryVer);
}
//<2F><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>
VOID * CTraceService::GetTraceServiceManager(const IID & Guid, DWORD dwQueryVer)
{
return NULL;
}
//״̬<D7B4><CCAC><EFBFBD><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//׷<><D7B7>״̬
bool CTraceService::IsEnableTrace(enTraceLevel TraceLevel)
{
return false;
}
//׷<>ٿ<EFBFBD><D9BF><EFBFBD>
bool CTraceService::EnableTrace(enTraceLevel TraceLevel, bool bEnableTrace)
{
return false;
}
//׷<>ٿ<EFBFBD><D9BF><EFBFBD>
bool CTraceService::EnableAllTrace( bool bEnableTrace )
{
if (g_bEnableTrace!=bEnableTrace)
{
g_bEnableTrace=bEnableTrace;
return true;
}
return false;
}
//<2F><><EFBFBD>ܺ<EFBFBD><DCBA><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//׷<><D7B7><EFBFBD><EFBFBD>Ϣ
bool CTraceService::TraceString(LPCTSTR pszString, enTraceLevel TraceLevel)
{
if (g_pITraceService!=NULL && pszString!=NULL && *pszString!=0)
{
return g_pITraceService->TraceString(pszString, TraceLevel);
}
return false;
}
bool CTraceService::TraceFormat( enTraceLevel TraceLevel, LPCTSTR pszFormat,... )
{
if (g_bEnableTrace && g_pITraceService!=NULL && pszFormat!=NULL && *pszFormat!=0)
{
CString str;
va_list ptr;
va_start(ptr, pszFormat);
str.FormatV(pszFormat,ptr);
va_end(ptr);
return g_pITraceService->TraceString(str, TraceLevel);
}
return false;
}
//////////////////////////////////////////////////////////////////////////
//׷<>ٷ<EFBFBD><D9B7><EFBFBD>
//////////////////////////////////////////////////////////////////////////
#define WM_TRACE_STRING WM_USER+1
BEGIN_MESSAGE_MAP(CTraceServiceControl, CRichEditCtrl)
ON_WM_RBUTTONDOWN()
ON_WM_CREATE()
ON_WM_DESTROY()
ON_MESSAGE(WM_TRACE_STRING,OnTraceServiceMessage)
ON_COMMAND(IDM_MENU0, OnCopyString)
ON_COMMAND(IDM_MENU1, OnSelectAll)
ON_COMMAND(IDM_MENU2, OnDeleteString)
ON_COMMAND(IDM_MENU3, OnClearAll)
ON_COMMAND(IDM_MENU4, OnSaveString)
END_MESSAGE_MAP()
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//д<><D0B4><EFBFBD><EFBFBD>־
void AutoSaveLog(CTraceServiceControl *pRichEditTrace)
{
static CString strLogPath;
if (strLogPath.IsEmpty())
{
TCHAR szBuf[MAX_PATH];
GetModuleFileName(NULL,szBuf,CountString(szBuf));
PathRemoveExtension(szBuf);
LPTSTR pszFileName=::PathFindFileName(szBuf);
CString strFileName(pszFileName);
StringCchCopy(pszFileName,CountString(szBuf)-(pszFileName-szBuf),_T("ServerLog"));
if (!::PathFileExists(szBuf))
{
return;
}
if (strFileName.CompareNoCase(_T("GameServer"))==0)
{
AfxGetMainWnd()->GetWindowText(strFileName);
strFileName.MakeLower();
strFileName.Replace(_T(".rop"),_T(""));
strFileName.Replace(_T("[<5B><><EFBFBD>سɹ<D8B3>]"),_T(""));
strFileName.Replace(_T("[<5B><><EFBFBD><EFBFBD>ʧ<EFBFBD><CAA7>]"),_T(""));
strFileName.Replace(_T("[ֹͣ]"),_T(""));
}
//<2F><>ȡʱ<C8A1><CAB1>
SYSTEMTIME st;
GetLocalTime(&st);
strLogPath.Format(_T("%s\\%s%04d%02d%02d%02d%02d%02d%03d.log"),szBuf,strFileName,
st.wYear, st.wMonth, st.wDay, st.wHour, st.wMinute, st.wSecond,st.wMilliseconds);
}
try
{
CString strInput;
pRichEditTrace->GetWindowText(strInput);
if (!strInput.IsEmpty())
{
CFile file;
if (file.Open(strLogPath, CFile::modeCreate|CFile::modeWrite|CFile::typeBinary|CFile::modeNoTruncate))
{
file.SeekToEnd();
file.Write(strInput, strInput.GetLength()*sizeof(TCHAR));
file.Close();
}
}
}
catch(...)
{
ASSERT(0);
}
}
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD><EFBFBD><ECBAAF>
CTraceServiceControl::CTraceServiceControl()
{
CTraceService::SetTraceService((IUnknownEx*)QueryInterface(IID_IUnknownEx, VER_IUnknownEx));
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
CTraceServiceControl::~CTraceServiceControl()
{
CTraceService::SetTraceService(NULL);
g_aryTraceStringStorage.Append(g_aryTraceString);
for ( INT_PTR i=g_aryTraceStringStorage.GetCount()-1; i>=0; i-- )
{
tagTraceString *pTraceString=g_aryTraceStringStorage[i];
SafeDelete(pTraceString);
}
}
//<2F><><EFBFBD><EFBFBD><EFBFBD>ӿ<EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F>ӿڲ<D3BF>ѯ
VOID * CTraceServiceControl::QueryInterface(const IID & Guid, DWORD dwQueryVer)
{
QUERYINTERFACE(ITraceService, Guid, dwQueryVer);
QUERYINTERFACE_IUNKNOWNEX(ITraceService, Guid, dwQueryVer);
return NULL;
}
//<2F><>Ϣ<EFBFBD>ӿ<EFBFBD>
//////////////////////////////////////////////////////////////////////////
//׷<><D7B7><EFBFBD><EFBFBD>Ϣ
bool CTraceServiceControl::TraceString(LPCTSTR pszString, enTraceLevel TraceLevel)
{
//Ч<><D0A7><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
ITraceService *pITraceService = QUERY_ME_INTERFACE(ITraceService);
VERIFY_RETURN_FALSE(pITraceService != NULL);
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
tagTraceString *pTraceString=NULL;
g_CS.Lock();
INT_PTR iIndex=g_aryTraceStringStorage.GetCount()-1;
if (iIndex>=0)
{
pTraceString=g_aryTraceStringStorage[iIndex];
g_aryTraceStringStorage.RemoveAt(iIndex);
}
g_CS.Unlock();
if (NULL==pTraceString)
{
pTraceString=new tagTraceString;
}
VERIFY_RETURN_FALSE(pTraceString!=NULL);
//<2F><>ȡʱ<C8A1><CAB1>
SYSTEMTIME SystemTime;
GetLocalTime(&SystemTime);
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
pTraceString->enTL=TraceLevel;
pTraceString->strMsg.Format(TEXT("<EFBFBD><EFBFBD> %04d-%02d-%02d %02d:%02d:%02d <20><>%s\n"), SystemTime.wYear, \
SystemTime.wMonth, SystemTime.wDay, SystemTime.wHour, SystemTime.wMinute, SystemTime.wSecond,pszString);
//<2F><><EFBFBD>ӵ<EFBFBD><D3B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
iIndex=-1;
g_CS.Lock();
iIndex=g_aryTraceString.Add(pTraceString);
g_CS.Unlock();
if (0==iIndex)
{
PostMessage(WM_TRACE_STRING,0,0);
}
return true;
}
//<2F><><EFBFBD>غ<EFBFBD><D8BA><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F>󶨺<EFBFBD><F3B6A8BA><EFBFBD>
VOID CTraceServiceControl::PreSubclassWindow()
{
__super::PreSubclassWindow();
CTraceService::SetTraceService((IUnknownEx*)QueryInterface(IID_IUnknownEx, VER_IUnknownEx));
}
//<2F><><EFBFBD>ܺ<EFBFBD><DCBA><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
bool CTraceServiceControl::LoadMessage(LPCTSTR pszFileName)
{
if (static_cast<CTraceServiceControl*>(g_pITraceService) == NULL) return false;
return static_cast<CTraceServiceControl*>(g_pITraceService)->LoadMessage(pszFileName);
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
bool CTraceServiceControl::SaveMessage(LPCTSTR pszFileName)
{
if (static_cast<CTraceServiceControl*>(g_pITraceService) == NULL) return false;
return static_cast<CTraceServiceControl*>(g_pITraceService)->SaveMessage(pszFileName);
}
//<2F><><EFBFBD>ò<EFBFBD><C3B2><EFBFBD>
bool CTraceServiceControl::SetParameter(LONG lMaxLineCount, LONG lReserveLineCount)
{
m_lMaxLineCount = lMaxLineCount; //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
m_lReserveLineCount = lReserveLineCount; //<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
return true;
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD>÷<EFBFBD><C3B7><EFBFBD>
VOID CTraceServiceControl::InitializeService()
{
}
//<2F><>ȡ<EFBFBD><C8A1>ɫ
COLORREF CTraceServiceControl::GetTraceColor(enTraceLevel TraceLevel)
{
switch (TraceLevel)
{
case TraceLevel_Info : return RGB(15, 130, 248);
case TraceLevel_Normal : return RGB(133, 124, 129);
case TraceLevel_Warning : return RGB(232,100,27);
case TraceLevel_Exception : return RGB(255,0,0);
case TraceLevel_Debug : return RGB(19, 127, 140);
}
return RGB(0, 0, 0);
}
//<2F>ַ<EFBFBD><D6B7>ж<EFBFBD>
bool EfficacyUrlChar(TCHAR chChar)
{
//<2F><><EFBFBD><EFBFBD><EFBFBD>ַ<EFBFBD>
if (chChar == TEXT('.')) return true;
if (chChar == TEXT('=')) return true;
if (chChar == TEXT('+')) return true;
if (chChar == TEXT('?')) return true;
if (chChar == TEXT('#')) return true;
if (chChar == TEXT('%')) return true;
if (chChar == TEXT('/')) return true;
if (chChar == TEXT(':')) return true;
if (chChar == TEXT('&')) return true;
//<2F>ַ<EFBFBD><D6B7><EFBFBD>Χ
if ((chChar >= TEXT('a')) && (chChar <= TEXT('z'))) return true;
if ((chChar >= TEXT('A')) && (chChar <= TEXT('Z'))) return true;
if ((chChar >= TEXT('0')) && (chChar <= TEXT('9'))) return true;
return false;
}
//<2F><>ַ<EFBFBD>ж<EFBFBD>
bool EfficacyUrlString(LPCTSTR pszUrl)
{
for (WORD i = 0; i < lstrlen(pszUrl); i++)
{
if (!EfficacyUrlChar(pszUrl[i])) return false;
}
return true;
}
//<2F><><EFBFBD><EFBFBD><EFBFBD>ִ<EFBFBD>
bool CTraceServiceControl::InsertString(LPCTSTR pszString, CHARFORMAT2 & CharFormat)
{
if (GetTextLength() >= 0x80000)//1024 * 512
{
OnClearAll();
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
bool bResumeSelect;
CHARRANGE CharRange;
//<2F><><EFBFBD><EFBFBD>״̬
SetSel(-1L, -1L);
GetSel(CharRange.cpMin, CharRange.cpMax);
bResumeSelect = (CharRange.cpMax != CharRange.cpMin);
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
LPCTSTR pszHttp = TEXT("http://");
const INT nHttpLength = lstrlen(pszHttp);
const INT nStringLength = lstrlen(pszString);
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
INT nStringStart = 0;
INT nStringPause = 0;
//<2F>ַ<EFBFBD><D6B7><EFBFBD><EFBFBD><EFBFBD>
for (INT i = 0; i < nStringLength; i++)
{
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
INT nUrlPause = i;
//<2F><>ַ<EFBFBD>ж<EFBFBD>
if (((i + nHttpLength) < nStringLength) && (memcmp(&pszString[i], pszHttp, nHttpLength*sizeof(TCHAR)) == 0))
{
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
nUrlPause = i + nHttpLength;
//<2F><>ַ<EFBFBD><D6B7><EFBFBD><EFBFBD>
while (nUrlPause < nStringLength)
{
//<2F>ַ<EFBFBD><D6B7>ж<EFBFBD>
if (EfficacyUrlChar(pszString[nUrlPause]))
{
nUrlPause++;
continue;
}
break;
}
}
//<2F><>ֹ<EFBFBD>ַ<EFBFBD>
if (nUrlPause <= (i + nHttpLength)) nStringPause = (i + 1);
//<2F><><EFBFBD><EFBFBD><EFBFBD>ַ<EFBFBD>
if ((i == (nStringLength - 1)) || (nUrlPause > (i + nHttpLength)))
{
//<2F><>ͨ<EFBFBD>ַ<EFBFBD>
if (nStringPause > nStringStart)
{
//<2F><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>
CString strNormalString;
LPTSTR pszNormalString = strNormalString.GetBuffer(nStringPause - nStringStart + 1);
//<2F><><EFBFBD><EFBFBD><EFBFBD>ַ<EFBFBD>
pszNormalString[nStringPause-nStringStart] = 0;
CopyMemory(pszNormalString, &pszString[nStringStart], (nStringPause - nStringStart)*sizeof(TCHAR));
//<2F>ͷŻ<CDB7><C5BB><EFBFBD>
strNormalString.ReleaseBuffer();
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
SetSel(-1L, -1L);
SetWordCharFormat(CharFormat);
ReplaceSel((LPCTSTR)strNormalString);
}
//<2F><><EFBFBD>ӵ<EFBFBD>ַ
if (nUrlPause > (i + nHttpLength))
{
//<2F><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>
CString strUrlString;
LPTSTR pszUrlString = strUrlString.GetBuffer((nUrlPause - i) + 1);
//<2F><><EFBFBD><EFBFBD><EFBFBD>ַ<EFBFBD>
pszUrlString[nUrlPause-i] = 0;
CopyMemory(pszUrlString, &pszString[i], (nUrlPause - i)*sizeof(TCHAR));
//<2F>ͷŻ<CDB7><C5BB><EFBFBD>
strUrlString.ReleaseBuffer();
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʽ
CHARFORMAT2 CharFormatHyper;
CharFormatHyper = CharFormat;
//Ч<><D0A7><EFBFBD><EFBFBD>ַ
if (EfficacyUrlString(strUrlString))
{
CharFormatHyper.dwMask |= CFM_LINK;
CharFormatHyper.dwEffects |= CFE_LINK;
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
SetSel(-1L, -1L);
SetWordCharFormat(CharFormatHyper);
ReplaceSel((LPCTSTR)strUrlString);
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
nStringStart = __max(i, nUrlPause);
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
i += (nUrlPause - i);
}
//״̬<D7B4><CCAC><EFBFBD><EFBFBD>
if (bResumeSelect)
{
SetSel(CharRange);
}
else
{
PostMessage(WM_VSCROLL, SB_BOTTOM, 0);
}
return true;
}
//<2F>ص<EFBFBD><D8B5><EFBFBD><EFBFBD><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD>ػص<D8BB>
DWORD CALLBACK CTraceServiceControl::LoadCallBack(DWORD dwCookie, LPBYTE pbBuff, LONG cb, LONG * pcb)
{
return 0;
}
//<2F><><EFBFBD><EFBFBD><EFBFBD>ص<EFBFBD>
DWORD CALLBACK CTraceServiceControl::SaveCallBack(DWORD dwCookie, LPBYTE pbBuff, LONG cb, LONG * pcb)
{
return 0;
}
//<2F>˵<EFBFBD><CBB5><EFBFBD><EFBFBD><EFBFBD>
//////////////////////////////////////////////////////////////////////////
//ɾ<><C9BE><EFBFBD><EFBFBD>Ϣ
VOID CTraceServiceControl::OnClearAll()
{
AutoSaveLog(this);
SetWindowText(NULL);
}
//ȫ<><C8AB>ѡ<EFBFBD><D1A1>
VOID CTraceServiceControl::OnSelectAll()
{
__super::SetSel(0, __super::GetTextLength());
}
//<2F><><EFBFBD><EFBFBD><EFBFBD>ַ<EFBFBD>
VOID CTraceServiceControl::OnCopyString()
{
__super::Copy();
}
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
VOID CTraceServiceControl::OnSaveString()
{
CFileDialog dlg(FALSE, _T("*.txt"), NULL, 4 | 2, _T("<EFBFBD><EFBFBD>Ϣ|*.txt||"));
if (dlg.DoModal() == IDOK)
{
CFile file;
if (file.Open(dlg.GetPathName(), CFile::modeCreate | CFile::modeWrite))
{
CString strInput;
GetWindowText(strInput);
file.Write(strInput, strInput.GetLength());
file.Close();
}
}
}
//ɾ<><C9BE><EFBFBD>ַ<EFBFBD>
VOID CTraceServiceControl::OnDeleteString()
{
ReplaceSel(NULL, true);
}
//<2F><>Ϣӳ<CFA2><D3B3>
//////////////////////////////////////////////////////////////////////////
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
INT CTraceServiceControl::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (__super::OnCreate(lpCreateStruct)==-1)
{
return -1;
}
return 0;
}
//<2F>Ҽ<EFBFBD><D2BC><EFBFBD>Ϣ
VOID CTraceServiceControl::OnRButtonDown(UINT nFlags, CPoint point)
{
CMenu menu;
ClientToScreen(&point);
menu.CreatePopupMenu();
CHARRANGE sl;
GetSel(sl);
menu.AppendMenu(MF_STRING | (sl.cpMax != sl.cpMin) ? 0 : MF_DISABLED | MF_GRAYED, IDM_MENU0, _T("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>(&C)\tCtrl+C"));
menu.AppendMenu(MF_STRING | (GetTextLength() > 0 && sl.cpMax - sl.cpMin < GetTextLength()) ? 0 : MF_DISABLED | MF_GRAYED, IDM_MENU1, _T("ȫѡ(&A)\tCtrl+A"));
menu.AppendMenu(MF_STRING | (false) ? 0 : MF_DISABLED | MF_GRAYED, IDM_MENU2, _T("ɾ<EFBFBD><EFBFBD>(&D)"));
menu.AppendMenu(MF_STRING | (GetTextLength() > 0) ? 0 : MF_DISABLED | MF_GRAYED, IDM_MENU3, _T("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ"));
menu.AppendMenu(MF_SEPARATOR, 0);
menu.AppendMenu(MF_STRING | (GetTextLength() > 0) ? 0 : MF_DISABLED | MF_GRAYED, IDM_MENU4, _T("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ..."));
TrackPopupMenu(menu.m_hMenu, nFlags, point.x, point.y, 0, m_hWnd, NULL);
}
//׷<><D7B7><EFBFBD><EFBFBD>Ϣ
LRESULT CTraceServiceControl::OnTraceServiceMessage(WPARAM wParam, LPARAM lParam)
{
if (g_aryTraceString.IsEmpty())
{
return 0;
}
CWHArray<tagTraceString *> ary;
//<2F><>ȡ<EFBFBD><C8A1>ǰ׷<C7B0><D7B7><EFBFBD><EFBFBD>Ϣ
g_CS.Lock();
ary.Append(g_aryTraceString);
g_aryTraceString.RemoveAll();
g_CS.Unlock();
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
CHARFORMAT2 CharFormat;
ZeroMemory(&CharFormat, sizeof(CharFormat));
//<2F><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
CharFormat.cbSize = sizeof(CharFormat);
CharFormat.dwMask = CFM_COLOR | CFM_BACKCOLOR;
CharFormat.crTextColor = RGB(0, 0, 0);
CharFormat.crBackColor = RGB(255, 255, 255);
StringCchCopy(CharFormat.szFaceName, CountString(CharFormat.szFaceName), TEXT("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>"));
for ( INT_PTR i=0,n=ary.GetCount(); i<n; i++ )
{
tagTraceString *pTraceString=ary[i];
CharFormat.crTextColor = GetTraceColor(pTraceString->enTL);
InsertString(pTraceString->strMsg, CharFormat);
}
//<2F>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD><EFBFBD>
g_CS.Lock();
g_aryTraceStringStorage.Append(ary);
g_CS.Unlock();
return 0;
}
void CTraceServiceControl::OnDestroy()
{
AutoSaveLog(this);
return __super::OnDestroy();
}