12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013 |
- #include "precompile.h"
- #include "sp_gui.h"
- #include "sp_def.h"
- #include "memutil.h"
- #include "log_define.h"
- #ifdef _WIN32
- #include <tchar.h>
- #include "resource1.h"
- #include <atlbase.h>
- #include <gdiplus.h>
- using namespace Gdiplus;
- #include "resource1.h"
- #include "sp_checkEntity.h"
- #endif //_WIN32
- #include "SimpleString.h"
- #include <string>
- #include <list>
- using namespace std;
- #include "sp_env.h"
- #include "array.h"
- #include "sp_cfg.h"
- #include "SpBase.h"
- #include <winpr/wtypes.h>
- #define SHELL_WND_CLS "SpShell_Wnd"
- #define BLUE_COLOR RGB(0, 0, 255)
- #define WHITE_COLOR RGB(255,255, 255)
- #define RED_COLOR RGB(255,0, 0)
- #define WM_DISPLAY (WM_APP+1)
- #define WM_UNDISPLAY (WM_APP+2)
- #define FONT_SMALL_SIZE 20 // show message in a big font
- #define FONT_LARGE_SIZE 48 // show message in a big font
- int g_guiShowFirst = 1;
- struct sp_gui_t
- {
- #ifdef _WIN32
- HINSTANCE hInst;
- HWND hWnd;
- HWND hWndEditBox;
- HFONT hSmallFont;
- HFONT hLargeFont;
- //HPEN hPen;
- HBRUSH hBkBrush;
- BOOL bShow;
- HANDLE hThreadWorker;
- int iNotifyResult;
- HANDLE hEventNotify;
- BOOL bBlueScreen;
- ULONG_PTR pGDIToken;
- #endif // _WIN32
- };
- #ifdef _WIN32
- static LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);
- static int GetTotalEntityCount()
- {
- auto env = sp_get_env();
- if (env == NULL) {
- return getEntityResource()->m_EntityCount;
- }
- auto cfg = env->cfg;
- if (cfg == NULL) {
- return getEntityResource()->m_EntityCount;
- }
- return cfg->shell_ini->arr_entity->nelts;
- }
- static const wchar_t *GetTerminalInfo()
- {
- static wchar_t wszInfo[256] = {};
- if (wszInfo[0] != 0)
- return wszInfo;
- auto env = sp_get_env();
- if (env == NULL) {
- return NULL;
- }
- auto cfg = env->cfg;
- if (cfg == NULL) {
- return NULL;
- }
- swprintf(wszInfo, L"%S %S V%d.%d.%d.%d",
- cfg->root_ini->terminal_no == NULL ? "" : cfg->root_ini->terminal_no,
- cfg->root_ini->site == NULL ? "" : cfg->root_ini->site,
- cfg->install_ini->install_version.major,
- cfg->install_ini->install_version.minor,
- cfg->install_ini->install_version.revision,
- cfg->install_ini->install_version.build);
- return wszInfo;
- }
- static int OnCreate(sp_gui_t *gui, HWND hWnd, WPARAM wParam, LPARAM lParam)
- {
- HDC hdc;
- long lfHeight;
- LPCREATESTRUCTA lpCreateStruct = (LPCREATESTRUCTA)lParam;
- int nLogPixelsY;
-
- //gui->hWndEditBox = CreateWindowA("STATIC", "", WS_VISIBLE | WS_CHILD/*|SS_CENTER*/, 20, 20,
- // lpCreateStruct->cx - 20, lpCreateStruct->cy - 20, hWnd, (HMENU)101, gui->hInst, NULL);
- //gui->hWndEditBox = CreateWindowA("EDIT", "", WS_VISIBLE | WS_CHILD | ES_READONLY | ES_MULTILINE | ES_AUTOVSCROLL,
- // 10, 10, lpCreateStruct->cx - 20, lpCreateStruct->cy - 20, hWnd, (HMENU)101, gui->hInst, NULL);
- hdc = GetDC(NULL);
- nLogPixelsY = GetDeviceCaps(hdc, LOGPIXELSY);
- ReleaseDC(NULL, hdc);
- lfHeight = -MulDiv(FONT_SMALL_SIZE, nLogPixelsY, 72);
- //gui->hSmallFont = CreateFontA(lfHeight, 0, 0, 0, 0, FALSE, 0, 0, 0, 0, 0, 0, 0, "Times New Roman");
- gui->hSmallFont = CreateFontA(lfHeight, 0, 0, 0, 0, FALSE, 0, 0, 0, 0, 0, 0, 0, "微软雅黑");
- lfHeight = -MulDiv(FONT_LARGE_SIZE, nLogPixelsY, 72);
- //gui->hLargeFont = CreateFontA(lfHeight, 0, 0, 0, 0, FALSE, 0, 0, 0, 0, 0, 0, 0, "Times New Roman");
- gui->hLargeFont = CreateFontA(lfHeight, 0, 0, 0, 0, FALSE, 0, 0, 0, 0, 0, 0, 0, "微软雅黑");
-
- //SetWindowLong(hWnd, GWL_EXSTYLE, GetWindowLong(hWnd, GWL_EXSTYLE) | WS_EX_LAYERED | WS_EX_TRANSPARENT);
- return 0;
- }
- static int OnDestroy(sp_gui_t *gui, HWND hWnd, WPARAM wParam, LPARAM lParam)
- {
- DestroyWindow(gui->hWndEditBox);
- gui->hWndEditBox = NULL;
- DeleteObject(gui->hSmallFont);
- DeleteObject(gui->hLargeFont);
- PostQuitMessage(0);
- return 0;
- }
- typedef void (WINAPI *PSwitchToThisWindow)(HWND, BOOL);
- static int init(sp_gui_t *gui)
- {
- //GdiPlus初始化
- GdiplusStartupInput gdiplusInput;
- GdiplusStartup(&gui->pGDIToken, &gdiplusInput, NULL);
- // 窗口类注册
- WNDCLASSA wc = {0};
- gui->hInst = GetModuleHandleA(NULL);
- gui->hBkBrush = wc.hbrBackground = CreateSolidBrush(BLUE_COLOR);
- wc.hCursor = LoadCursorA(NULL, MAKEINTRESOURCEA(IDC_ARROW));
- wc.hIcon = LoadIconA(NULL, MAKEINTRESOURCEA(IDI_APPLICATION));
- wc.hInstance = gui->hInst;
- wc.lpfnWndProc = &WndProc;
- wc.lpszClassName = SHELL_WND_CLS;
- wc.style = CS_HREDRAW | CS_VREDRAW;
- if (RegisterClassA(&wc) == 0)
- return -1;
- gui->hWnd = CreateWindowExA(WS_EX_TOOLWINDOW, wc.lpszClassName, "", WS_POPUP|WS_BORDER,
- 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), NULL, NULL, gui->hInst, gui);
- if (gui->hWnd == NULL)
- return Error_Unexpect;
- gui->bShow = TRUE;
- RegisterTouchWindow(gui->hWnd, 0); // support WM_TOUCH
- ShowWindow(gui->hWnd, g_guiShowFirst ? SW_SHOW : SW_HIDE);
- UpdateWindow(gui->hWnd);
- //BringWindowToTop(gui->hWnd);
- //SetWindowPos(gui->hWnd, HWND_TOP, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE);
- return 0;
- }
- static int term(sp_gui_t *gui)
- {
- //DestroyWindow(gui->hWnd);
- //gui->hWnd = NULL;
- UnregisterClassA(SHELL_WND_CLS, gui->hInst);
- DeleteObject(gui->hBkBrush);
- gui->hBkBrush = NULL;
- //GdiPlus 取消初始化
- GdiplusShutdown(gui->pGDIToken);
- return 0;
- }
- static unsigned int __stdcall work_proc(void *param)
- {
- sp_gui_t *gui = (sp_gui_t*)param;
- int rc;
- MSG msg;
- rc = init(gui);
- gui->iNotifyResult = rc;
- SetEvent(gui->hEventNotify);
- if (rc != 0)
- return rc;
- //--> will disable the Display and Sleep Idle Timeouts .
- SetThreadExecutionState(ES_CONTINUOUS | ES_SYSTEM_REQUIRED | ES_DISPLAY_REQUIRED);
- while (GetMessageA(&msg, NULL, 0, 0)) {
- TranslateMessage(&msg);
- DispatchMessageA(&msg);
- }
- SetThreadExecutionState(ES_CONTINUOUS);
- term(gui);
- return 0;
- }
- // 从资源中读出Logo
- static int LoadLogoImage(int nResourceID, Image *&pImage)
- {
- auto hMod = GetModuleHandle("spbase");
- auto hResInfo = FindResource(hMod, MAKEINTRESOURCE(nResourceID), TEXT("PNG"));
- if (hResInfo == NULL)
- return 1;
- auto hResData = LoadResource(hMod, hResInfo);
- if (hResData == NULL)
- return 2;
- auto pResData = LockResource(hResData);
- if (pResData == NULL)
- return 3;
- int iSize = SizeofResource(hMod, hResInfo);
- if (iSize <= 0)
- return 4;
- HGLOBAL hMem = ::GlobalAlloc(GMEM_MOVEABLE, iSize);
- if (!hMem)
- {
- UnlockResource(hResData);
- return 5;
- }
- LPVOID pTemp = ::GlobalLock(hMem);
- if (pTemp == NULL)
- {
- UnlockResource(hResData);
- GlobalFree(hMem);
- return 6;
- }
- // copy data
- memcpy(pTemp, pResData, iSize);
- ::GlobalUnlock(hMem);
- UnlockResource(hResData);
- CComPtr<IStream> spStream;
- HRESULT hr = ::CreateStreamOnHGlobal(hMem, TRUE, &spStream);
- if (!SUCCEEDED(hr))
- {
- GlobalFree(hMem);
- return 7;
- }
- pImage = Image::FromStream(spStream);
- if (pImage == NULL)
- return 8;
- return 0;
- }
- static int DrawConsoleTitle(Graphics &graphics, int nLeftWidth, int nRightWidth)
- {
- FontFamily fontFamily(L"宋体");
- Font font(&fontFamily, 18, FontStyleBold, UnitPoint);
- RectF rectF(nLeftWidth, 0, nRightWidth, nRightWidth / 3);
- StringFormat format;
- format.SetAlignment(StringAlignmentCenter);
- format.SetLineAlignment(StringAlignmentCenter);
- SolidBrush fontBrush(Color(255, 67, 67, 67));
- CSimpleStringW strMsg= TEXT("招商银行视频柜台");
- graphics.DrawString(strMsg, strMsg.GetLength(), &font, rectF, &format, &fontBrush);
- return 0;
- }
- static int DrawBackground(Graphics &graphics, int nLeftWidth, int nRightWidth, int nHeight)
- {
- // draw left
- SolidBrush leftBrush(Color(255, 101, 105, 108));
- Pen leftPen(&leftBrush);
- graphics.DrawRectangle(&leftPen, 0, 0, nLeftWidth, nHeight);
- graphics.FillRectangle(&leftBrush, 0, 0, nLeftWidth, nHeight);
- // draw right
- SolidBrush rightBrush(Color(255, 161, 163, 165));
- Pen rightPen(&rightBrush);
- graphics.DrawRectangle(&rightPen, nLeftWidth, 0, nRightWidth, nHeight);
- graphics.FillRectangle(&rightBrush, nLeftWidth, 0, nRightWidth, nHeight);
- // draw logo
- Image *pLogoImage = NULL;
- if (LoadLogoImage(IDB_VTMLOGO, pLogoImage) !=0)
- {
- // 直接输出可视柜台文字
- DrawConsoleTitle(graphics, nLeftWidth, nRightWidth);
- }
- else
- {
- graphics.DrawImage(pLogoImage, nLeftWidth + nRightWidth / 8, 20, nRightWidth * 3 / 4, nRightWidth * 3 / 4 / 3);
- }
- delete pLogoImage;
-
- return 0;
- }
- static int DrawLineString(Graphics &graphics, wstring &msg, Font *font, RectF &rect, StringFormat *format, Brush *brush, int nLineSpace, int &nNextLinePosY)
- {
- nNextLinePosY = rect.Y;
- // 一次最多32个
- CharacterRange crs[32];
- for (int i = 0; i < 32; i++)
- {
- crs[i].First = i;
- crs[i].Length = 1;
- }
- format->SetFormatFlags(StringFormatFlagsNoClip);
- // 当前输出区域
- RectF layoutRect = rect;
- int nDelta = 60; // 每行输出留白空间
- int nFrom = 0;
- int nLineCount = 0;
- int nTotalWidth = 0;
- int nLineHeight = 0;
- int nMsgLen = msg.length();
-
- while (nFrom + nLineCount < nMsgLen)
- {
- Region regions[32] = {};
- int nCount = 32;
- if (nFrom + nLineCount + nCount > nMsgLen)
- nCount = nMsgLen - nFrom - nLineCount;
- format->SetMeasurableCharacterRanges(nCount, crs);
- //tempMsg = msg.substr(nFrom + nLineCount, nCount);
- graphics.MeasureCharacterRanges(msg.data() + nFrom + nLineCount, nCount, font, layoutRect, format, nCount, regions);
-
- for (int i = 0; i < nCount; i++)
- {
- Rect r;
- regions[i].GetBounds(&r, &graphics);
- nTotalWidth += r.Width;
- if (r.Height > nLineHeight)
- nLineHeight = r.Height;
- if (nTotalWidth <= layoutRect.Width - nDelta && msg[nFrom + nLineCount] != TEXT('\r') && msg[nFrom + nLineCount] != TEXT('\n'))
- {
- nLineCount++;
- }
- else
- {
- if (msg[nFrom + nLineCount] == TEXT('\r') || msg[nFrom + nLineCount] == TEXT('\n'))
- {
- if (nFrom + nLineCount + 1 < nMsgLen
- && ((msg[nFrom + nLineCount] == TEXT('\r') && msg[nFrom + nLineCount + 1] == TEXT('\n'))
- || (msg[nFrom + nLineCount] == TEXT('\n') && msg[nFrom + nLineCount + 1] == TEXT('\r'))))
- {
- nLineCount += 2;
- i++;
- }
- else
- nLineCount++;
- }
- //auto wszLine = msg.substr(nFrom, nLineCount);
- graphics.DrawString(msg.data() + nFrom, nLineCount, font, layoutRect, format, brush);
- // reset vars
- nFrom += nLineCount;
- nLineCount = 0;
- nTotalWidth = 0;
- layoutRect.Y += nLineHeight + nLineSpace;
- //nLineHeight = 0;
- nNextLinePosY = layoutRect.Y;
- // 写满显示高度,直接返回
- if (layoutRect.Y >= rect.Y + rect.Height)
- return 0;
- }
- }
- }
- // output last line
- if (nLineCount > 0)
- {
- graphics.DrawString(msg.data() + nFrom, nLineCount, font, layoutRect, format, brush);
- nNextLinePosY += nLineHeight + nLineSpace;
- }
- return 0;
- }
- static int DrawRunningInfo(Graphics &graphics, int nLeftWidth, int nRightWidth, int nHeight)
- {
- // 全部输出
- // get lock
- auto entityRes = getEntityResource();
- while (InterlockedCompareExchange(&entityRes->m_Locking, 1, 0) == 1)
- {
- Sleep(100);
- }
- // draw left
- wstring strLeft;
- FontFamily fontFamily(L"微软雅黑");
- SolidBrush blackBrush(Color(255, 0, 0, 0));
- SolidBrush whiteBrush(Color(255, 255, 255, 255));
- SolidBrush redBrush(Color(255, 174, 0, 0));
- SolidBrush redBrush2(Color(255, 130, 0, 0));
-
- if (entityRes->m_InBlueScreenMode)
- {
- strLeft = entityRes->m_BlueScreenMsg;
- Font font(&fontFamily, 32, FontStyleBold, UnitPoint);
- StringFormat format;
- format.SetFormatFlags(StringFormatFlagsNoClip);
- format.SetLineAlignment(StringAlignmentCenter);
- RectF rectF(10, 10, nLeftWidth - 20, nHeight - 20);
-
- graphics.DrawString(strLeft.c_str(), strLeft.length(), &font, rectF, &format, &whiteBrush);
- }
- else
- {
- Font font(&fontFamily, 10, FontStyleRegular, UnitPoint);
- StringFormat format;
- int nNextLinePosY = 10;
- auto it = entityRes->m_OutputMsgs.rbegin();
- if (entityRes->m_InBrowseMode)
- {
- for (int i = 0; i < entityRes->m_SkipLineNum && i < (int)entityRes->m_OutputMsgs.size(); i++)
- it++;
- }
- for (; it != entityRes->m_OutputMsgs.rend() && nNextLinePosY < nHeight; it++)
- {
- auto &strLine = *it;
- // output
- Brush *brush = NULL;
- if (wcsstr(strLine.c_str(), L"] W:{") != NULL)
- brush = &whiteBrush;
- else if (wcsstr(strLine.c_str(), L"] E:{") != NULL)
- brush = &redBrush2;
- else
- brush = &blackBrush;
- RectF rectF(10, nNextLinePosY, nLeftWidth - 20, nHeight - 20);
- DrawLineString(graphics, strLine, &font, rectF, &format, brush, 5, nNextLinePosY);
- }
- }
- // draw right
- wstring strLostEntitys;
- wstring strSum;
- int nStartedCount = 0;
- int nLostCount = 0;
- int nToStartCount = 0;
- wchar_t strTmp[128] = {};
- for (int i = 0; i < entityRes->m_EntityCount; i++)
- {
- if (entityRes->m_EntitysInfo[i].EntityState >= 2 && entityRes->m_EntitysInfo[i].EntityState <= 4)
- {
- nStartedCount++;
- }
- else if (entityRes->m_EntitysInfo[i].EntityState == 6)
- {
- nLostCount++;
- swprintf_s(strTmp, 128, L" 模块[%s]启动失败\r\n", entityRes->m_EntitysInfo[i].EntityName.c_str());
- strLostEntitys += strTmp;
- }
- }
-
- // 输出终端号、场所、版本
- StringFormat centerFormat;
- centerFormat.SetAlignment(StringAlignmentCenter);
- auto wszTerminalInfo = GetTerminalInfo();
- if (wszTerminalInfo != NULL)
- {
- Font rfont(&fontFamily, 10, FontStyleRegular, UnitPoint);
- RectF rrectF(nLeftWidth + 10, 110, nRightWidth - 20, nHeight - 180);
- int nNextLinePosY;
- DrawLineString(graphics, wstring(wszTerminalInfo), &rfont, rrectF, ¢erFormat, &blackBrush, 20, nNextLinePosY);
- }
- // 实体启动成功计数
- Font rfont(&fontFamily, 12, FontStyleBold, UnitPoint);
- swprintf_s(strTmp, 128, L"%d/%d 个模块启动成功", nStartedCount, GetTotalEntityCount());
- strSum = strTmp;
- int nNextLinePosY;
- RectF rrectF(nLeftWidth + 10, 140, nRightWidth - 20, nHeight - 180);
- DrawLineString(graphics, strSum, &rfont, rrectF, ¢erFormat, &blackBrush, 20, nNextLinePosY);
- // 输出当前启动状态信息
- Font rfont2(&fontFamily, 11, FontStyleRegular, UnitPoint);
- if (entityRes->m_StartupInfo.length() > 0)
- {
- RectF rrectF2(nLeftWidth + 6, nNextLinePosY, nRightWidth, nHeight - 180);
- DrawLineString(graphics, entityRes->m_StartupInfo, &rfont2, rrectF2, ¢erFormat, &whiteBrush, 5, nNextLinePosY);
- nNextLinePosY += 10;
- }
- // 输出实体启动错误
- StringFormat rformat2;
- {
- RectF rrectF2(nLeftWidth + 30, nNextLinePosY, nRightWidth, nHeight - 200);
- DrawLineString(graphics, strLostEntitys, &rfont2, rrectF2, &rformat2, &redBrush, 5, nNextLinePosY);
- }
- // 输出严重错误信息
- for (auto it2 = entityRes->m_FatalMsgs.rbegin(); it2!= entityRes->m_FatalMsgs.rend() && nNextLinePosY < nHeight; it2++)
- {
- RectF rrectF2(nLeftWidth + 30, nNextLinePosY, nRightWidth, nHeight - 200);
- wstring strLine = L"\r\n 【" + *it2+ L"】";
- DrawLineString(graphics, strLine, &rfont2, rrectF2, &rformat2, &redBrush, 5, nNextLinePosY);
- }
-
- // release lock
- InterlockedExchange(&entityRes->m_Locking, 0);
- return 0;
- }
- static int RepaintWindow(HWND hWnd, bool bCanUseCache)
- {
- static RECT lastRect = {};
- static HDC hBkgMemDC = NULL;
- if (!g_guiShowFirst)
- return 0;
- RECT rect = {};
- GetClientRect(hWnd, &rect);
- HDC hDC = GetDC(hWnd);
- if (lastRect.right == rect.right && lastRect.bottom == rect.bottom && hBkgMemDC != NULL && bCanUseCache)
- {
- // copy mem dc to hwnd dc
- //MessageBox(NULL, TEXT("use cached dc"), NULL, 0);
- BitBlt(hDC, 0, 0, rect.right, rect.bottom, hBkgMemDC, 0, 0, SRCCOPY);
- ReleaseDC(hWnd, hDC);
- return 0;
- }
- if (hBkgMemDC != NULL)
- {
- DeleteDC(hBkgMemDC);
- hBkgMemDC = NULL;
- }
- lastRect = rect;
- int nWidth = rect.right - rect.left;
- int nHeight = rect.bottom - rect.top;
- int nRightWidth = nWidth / 3;
- if (nRightWidth > 450)
- nRightWidth = 450;
- int nLeftWidth = nWidth - nRightWidth;
- hBkgMemDC = CreateCompatibleDC(hDC);
- auto hMemBitmap = CreateCompatibleBitmap(hDC, nWidth, nHeight);
- auto hOldObject = SelectObject(hBkgMemDC, hMemBitmap);
- Graphics graphics(hBkgMemDC);
- // draw background image
- DrawBackground(graphics, nLeftWidth, nRightWidth, nHeight);
- // draw output string
- DrawRunningInfo(graphics, nLeftWidth, nRightWidth, nHeight);
- // copy mem dc to hwnd dc
- BitBlt(hDC, 0, 0, rect.right, rect.bottom, hBkgMemDC, 0, 0, SRCCOPY);
- SelectObject(hBkgMemDC, hOldObject);
- DeleteObject(hMemBitmap);
- //DeleteDC(hBkgMemDC);
- ReleaseDC(hWnd, hDC);
- return 0;
- }
- static void SetBrowseModeShift(int nShiftLines)
- {
- if ((!getEntityResource()->m_InBrowseMode && nShiftLines <= 0) || getEntityResource()->m_OutputMsgs.size() <=20)
- return;
- // get lock
- auto entityRes = getEntityResource();
- while (InterlockedCompareExchange(&entityRes->m_Locking, 1, 0) == 1)
- {
- Sleep(100);
- }
-
- getEntityResource()->m_InBrowseMode = true;
- getEntityResource()->m_SkipLineNum += nShiftLines;
- if (nShiftLines > 0)
- {
- if (getEntityResource()->m_SkipLineNum + 20 > (int)getEntityResource()->m_OutputMsgs.size())
- {
- getEntityResource()->m_SkipLineNum = (int)getEntityResource()->m_OutputMsgs.size() - 20;
- }
- }
- else
- {
- if (getEntityResource()->m_SkipLineNum <= 0)
- {
- // 解除浏览模式
- getEntityResource()->m_SkipLineNum = 0;
- getEntityResource()->m_InBrowseMode = false;
- }
- }
-
- // release lock
- InterlockedExchange(&getEntityResource()->m_Locking, 0);
- }
- static LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
- {
- sp_gui_t *gui = NULL;
- static POINTS lastPoint = {};
- if (msg == WM_CREATE) {
- LPCREATESTRUCTA lpCreateStruct = (LPCREATESTRUCTA)lParam;
- gui = (sp_gui_t*)lpCreateStruct->lpCreateParams;
- SetWindowLongA(hWnd, GWL_USERDATA, (LONG)gui);
- }
- else {
- gui = (sp_gui_t*)GetWindowLongA(hWnd, GWL_USERDATA);
- }
- switch (msg) {
- case WM_CREATE:
- {
- if (OnCreate(gui, hWnd, wParam, lParam) != 0)
- return -1;
- }
- break;
- case WM_CLOSE:
- DestroyWindow(hWnd);
- break;
- case WM_MOUSEWHEEL:
- {
- getEntityResource()->m_LastShiftTick = GetTickCount();
- short sDelta = (short)HIWORD(wParam);
- SetBrowseModeShift(sDelta > 0 ? 10 : -10);
- RepaintWindow(hWnd, false);
- }
- break;
- case WM_TOUCH:
- {
- getEntityResource()->m_LastShiftTick = GetTickCount();
- DWORD nInputNum = (DWORD)wParam;
- TOUCHINPUT *tis = new TOUCHINPUT[nInputNum];\
- if (GetTouchInputInfo((HTOUCHINPUT)lParam, nInputNum, tis, sizeof(TOUCHINPUT)))
- {
- for (int i = 0; i < nInputNum; i++)
- {
- POINT pt = {};
- pt.x = TOUCH_COORD_TO_PIXEL(tis[i].x);
- pt.y = TOUCH_COORD_TO_PIXEL(tis[i].y);
- ScreenToClient(gui->hWnd, &pt);
- if (tis[i].dwFlags & TOUCHEVENTF_DOWN)
- {
- getEntityResource()->m_LastTouchID = tis[i].dwID;
- getEntityResource()->m_LastTouchYPos = pt.y;
- }
- else if (tis[i].dwFlags & TOUCHEVENTF_MOVE)
- {
- }
- else if (tis[i].dwFlags & TOUCHEVENTF_UP)
- {
- if (tis[i].dwID == getEntityResource()->m_LastTouchID)
- {
- SetBrowseModeShift(pt.y < getEntityResource()->m_LastTouchYPos ? 10 : -10);
- RepaintWindow(hWnd, false);
- getEntityResource()->m_LastTouchID = 0;
- getEntityResource()->m_LastTouchYPos = 0;
- }
- }
- }
- CloseTouchInputHandle((HTOUCHINPUT)lParam);
- delete[] tis;
- }
- }
- break;
- case WM_DESTROY:
- OnDestroy(gui, hWnd, wParam, lParam);
- break;
- case WM_PAINT:
- {
- PAINTSTRUCT ps;
- HDC hdc = BeginPaint(hWnd, &ps);
- RepaintWindow(hWnd, true);
- EndPaint(hWnd, &ps);
- }
- break;
- case WM_KEYDOWN:
- {
- if (wParam == VK_F3) { // hide
- SendMessageA(hWnd, WM_UNDISPLAY, 0, 0);
- }
- }
- break;
- case WM_CTLCOLORSTATIC:
- {
- HDC hDC = (HDC)wParam;
- HWND hWndControl = (HWND)lParam;
- SetBkColor(hDC, BLUE_COLOR);
- SetTextColor(hDC, WHITE_COLOR);
- return (LRESULT)gui->hBkBrush;
- }
- break;
- case WM_DISPLAY:
- {
- RepaintWindow(hWnd, false);
- if (getEntityResource()->m_InBlueScreenMode && !gui->bShow)
- {
- gui->bShow = TRUE;
- ShowWindow(gui->hWnd, SW_SHOW);
- }
- }
- break;
- case WM_UNDISPLAY:
- {
- DbgWithLink(LOG_LEVEL_INFO, LOG_TYPE_SYSTEM).setAPI(__FUNCTION__)("WM_UNDISPLAY, show gui undisplay");
- ShowWindow(hWnd, SW_HIDE);
- UpdateWindow(hWnd);
- gui->bShow = FALSE;
- }
- break;
- default:
- return DefWindowProc(hWnd, msg, wParam, lParam);
- }
- return 0;
- }
- #endif //_WIN32
- void sp_gui_setShow(int isShowFirst)
- {
- g_guiShowFirst = isShowFirst;
- }
- int sp_gui_create(sp_gui_t **p_gui)
- {
- sp_gui_t *gui = ZALLOC_T(sp_gui_t);
- #ifdef RVC_OS_WIN
- gui->hEventNotify = CreateEventA(NULL, TRUE, FALSE, NULL);
- if (!gui->hEventNotify)
- goto on_error;
- gui->hThreadWorker = (HANDLE)_beginthreadex(NULL, 0, &work_proc, gui, 0, NULL);
- if (!gui->hThreadWorker)
- goto on_error;
- WaitForSingleObject(gui->hEventNotify, INFINITE);
- if (gui->iNotifyResult)
- goto on_error;
- #endif //RVC_OS_WIN
- *p_gui = gui;
- return 0;
- #ifdef RVC_OS_WIN
- on_error :
- if (gui->hThreadWorker)
- CloseHandle(gui->hThreadWorker);
- if (gui->hEventNotify)
- CloseHandle(gui->hEventNotify);
- free(gui);
- return Error_Unexpect;
- #endif //RVC_OS_WIN
- }
- void sp_gui_destroy(sp_gui_t *gui)
- {
- #ifdef _WIN32
- PostMessageA(gui->hWnd, WM_CLOSE, 0, 0);
- WaitForSingleObject(gui->hThreadWorker, INFINITE);
- CloseHandle(gui->hThreadWorker);
- CloseHandle(gui->hEventNotify);
- #endif //_WIN32
- free(gui);
- }
- #if defined(_MSC_VER)
- int sp_gui_show_running_info(sp_gui_t* gui, const char* pMsg, int type)
- {
- // get lock
- auto entityRes = getEntityResource();
- while (InterlockedCompareExchange(&entityRes->m_Locking, 1, 0) == 1)
- Sleep(100);
- SYSTEMTIME st = {};
- GetLocalTime(&st);
- wchar_t szBuf[1024] = {};
- CSimpleStringA curMsg = pMsg;
- CSimpleStringW dstMsg = CSimpleStringA2W(curMsg);
- dstMsg = dstMsg.SubString(0, 1000);
- if (type == 1) {
- // bluescreen
- entityRes->m_InBlueScreenMode = true;
- swprintf_s(szBuf, 1024, L"%s\r\n", dstMsg.GetData());
- entityRes->m_BlueScreenMsg = szBuf;
- } else if (type == 2) {
- // fatal error
- swprintf_s(szBuf, 1024, L"%s", dstMsg.GetData());
- entityRes->m_FatalMsgs.push_back(szBuf);
- if (entityRes->m_FatalMsgs.size() > 100)
- entityRes->m_FatalMsgs.pop_front();
- } else if (type == 3) {
- // important startup info
- swprintf_s(szBuf, 1024, L"%s", dstMsg.GetData());
- entityRes->m_StartupInfo = szBuf;
- } else {
- // startup info
- swprintf_s(szBuf, 1024, L"[%02d:%02d:%02d] %s\r\n", st.wHour, st.wMinute, st.wSecond, dstMsg.GetData());
- entityRes->m_OutputMsgs.push_back(szBuf);
- // 只保留最近500条
- if (entityRes->m_OutputMsgs.size() > 500)
- entityRes->m_OutputMsgs.pop_front();
- }
- // browse mode continues 30s
- if (entityRes->m_InBrowseMode && GetTickCount() - entityRes->m_LastShiftTick >= 30000) {
- entityRes->m_InBrowseMode = false;
- entityRes->m_SkipLineNum = 0;
- }
- // release lock
- InterlockedExchange(&entityRes->m_Locking, 0);
- if (type >= 1 || (!entityRes->m_InBlueScreenMode && !entityRes->m_InBrowseMode)) {
- if (!PostMessageA(gui->hWnd, WM_DISPLAY, NULL, NULL)) {
- return Error_Unexpect;
- }
- }
- return 0;
- }
- int sp_gui_show_entity_info(sp_gui_t* gui, const char* entity, int state)
- {
- auto strEntity = CSimpleStringA2W(CSimpleStringA(entity));
- auto entityRes = getEntityResource();
- int i = 0;
- for (; i < entityRes->m_EntityCount; i++) {
- if (wcsicmp(strEntity, entityRes->m_EntitysInfo[i].EntityName.c_str()) == 0) {
- entityRes->m_EntitysInfo[i].EntityState = state;
- break;
- }
- }
- if (i == entityRes->m_EntityCount && entityRes->m_EntityCount < 80) {
- // new entity
- entityRes->m_EntitysInfo[i].EntityName = strEntity;
- entityRes->m_EntitysInfo[i].EntityState = state;
- entityRes->m_EntityCount++;
- }
- if (!PostMessageA(gui->hWnd, WM_DISPLAY, NULL, NULL)) {
- return Error_Unexpect;
- }
- return 0;
- }
- int sp_gui_display(sp_gui_t* gui)
- {
- if (!gui->bShow) {
- gui->bShow = TRUE;
- HWND hShellWnd = FindWindow(_T("Shell_TrayWnd"), NULL);
- if (hShellWnd != NULL)
- SendMessage(hShellWnd, WM_COMMAND, 419, 0);
- ShowWindow(gui->hWnd, SW_SHOW);
- }
- return 0;
- }
- int sp_gui_undisplay(sp_gui_t* gui)
- {
- getEntityResource()->m_InBlueScreenMode = false;
- if (!PostMessageA(gui->hWnd, WM_UNDISPLAY, 0, 0))
- return Error_Unexpect;
- return 0;
- }
- #else
- int sp_gui_create_format(sp_gui_format_t** p_gui)
- {
- int result = 0;
- sp_gui_format_t* gui = ZALLOC_T(sp_gui_format_t);
- sp_gui_t* inst = NULL;
- result = sp_gui_create(&inst);
- if (result == 0) {
- gui->gui_inst = inst;
- gui->display = &sp_gui_display;
- gui->hide = &sp_gui_undisplay;
- gui->show_entity_info = &sp_gui_show_entity_info;
- gui->show_running_info = &sp_gui_show_running_info;
- gui->post_message = &sp_gui_post_message;
- *p_gui = gui;
- } else {
- FREE(gui);
- }
- return result;
- }
- void sp_gui_destroy_format(sp_gui_format_t* p_gui)
- {
- sp_gui_destroy((sp_gui_t*)p_gui->gui_inst);
- FREE(p_gui);
- }
- int sp_gui_show_running_info(void* data, const char* pMsg, int type)
- {
- sp_gui_t* gui = (sp_gui_t*)data;
- return 0;
- }
- int sp_gui_show_entity_info(void* data, const char* entity, int state)
- {
- //void* data
- sp_gui_t* gui = (sp_gui_t*)data;
- return 0;
- }
- int sp_gui_display(void* data)
- {
- //void* data
- sp_gui_t* gui = (sp_gui_t*)data;
- return 0;
- }
- int sp_gui_undisplay(void* data)
- {
- //void* data
- sp_gui_t* gui = (sp_gui_t*)data;
- return 0;
- }
- void sp_gui_post_message(void* gui, unsigned long param1, unsigned long param2)
- {
- return;
- }
- #endif //_MSC_VER
|