From 6747bc043d0af20d6fa02a6cf385d81eb44643d0 Mon Sep 17 00:00:00 2001
From: LAPTOP-SNT8I5JK\Boounion <Chenluhua@qq.com>
Date: 星期六, 28 六月 2025 11:29:42 +0800
Subject: [PATCH] 1.自绘按钮,修改为支持文字在按钮下,或在按钮右。 2.日志页,修改为“包含”和“排除”关键字,以及正则表达式的支持,便于在调试过程中快速观察日志
---
SourceCode/Bond/Servo/Configuration.h | 2
SourceCode/Bond/Servo/BlButton.h | 2
SourceCode/Bond/Servo/PageLog.h | 11 ++
SourceCode/Bond/x64/Debug/Res/logcat_include.ico | 0
SourceCode/Bond/Servo/LogEdit.h | 2
SourceCode/Bond/Servo/Servo.rc | 0
SourceCode/Bond/Servo/PageLog.cpp | 62 ++++++++-------
SourceCode/Bond/Servo/Configuration.cpp | 11 ++
SourceCode/Bond/Servo/LogEdit.cpp | 64 ++++++++++-----
SourceCode/Bond/Servo/BlButton.cpp | 24 +++++-
SourceCode/Bond/Servo/ServoDlg.cpp | 7 +
11 files changed, 125 insertions(+), 60 deletions(-)
diff --git a/SourceCode/Bond/Servo/BlButton.cpp b/SourceCode/Bond/Servo/BlButton.cpp
index 2bddd2b..ff75530 100644
--- a/SourceCode/Bond/Servo/BlButton.cpp
+++ b/SourceCode/Bond/Servo/BlButton.cpp
@@ -36,6 +36,7 @@
m_hIcon[1] = nullptr;
m_nIconWidth = 0;
m_nFlashState = 0;
+ m_bTextRight = FALSE;
}
@@ -159,6 +160,11 @@
return m_nFlashState != 0;
}
+void CBlButton::SetTextRight()
+{
+ m_bTextRight = TRUE;
+}
+
void CBlButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
{
HDC hDC = lpDrawItemStruct->hDC;
@@ -200,15 +206,24 @@
HICON hIcon = this->IsWindowEnabled() ? m_hIcon[0] : m_hIcon[01];
if (hIcon != nullptr) {
int xIcon = (rcClient.right - rcClient.top - m_nIconWidth) / 2;
+ if (m_bTextRight) {
+ xIcon = 15;
+ }
+
if (m_hMenu != nullptr) xIcon -= 10;
int yIcon = (rcClient.bottom - rcClient.top - m_nIconWidth) / 2;
- if (nTextLen != 0) {
+ if (nTextLen != 0 && !m_bTextRight) {
yIcon -= 8;
}
DrawIconEx(hDC, xIcon, yIcon,
hIcon, m_nIconWidth, m_nIconWidth, 0, 0, DI_NORMAL);
- rcText.top = yIcon + m_nIconWidth + 2;
+ if (m_bTextRight) {
+ rcText.left = xIcon + m_nIconWidth + 2;
+ }
+ else {
+ rcText.top = yIcon + m_nIconWidth + 2;
+ }
}
@@ -223,18 +238,19 @@
::SetBkMode(hDC, TRANSPARENT);
::SetTextColor(hDC, m_crText[state]);
+ UINT format1 = m_bTextRight ? DT_LEFT : DT_CENTER;
if ((BS_MULTILINE & GetStyle()) == BS_MULTILINE) {
CRect rcBound;
int height = DrawTextA(hDC, szText, (int)strlen(szText), &rcBound, DT_CENTER | DT_CALCRECT | DT_EDITCONTROL);
rcText.top = rcBound.top + (rcClient.bottom - rcClient.top - height) / 2;
rcText.bottom = rcText.top + height;
- DrawTextA(hDC, szText, (int)strlen(szText), &rcText, DT_CENTER | DT_EDITCONTROL);
+ DrawTextA(hDC, szText, (int)strlen(szText), &rcText, format1 | DT_EDITCONTROL);
}
else {
if (m_hMenu != nullptr) {
rcText.right -= (10);
}
- DrawTextA(hDC, szText, (int)strlen(szText), &rcText, DT_VCENTER | DT_CENTER | DT_SINGLELINE | DT_END_ELLIPSIS);
+ DrawTextA(hDC, szText, (int)strlen(szText), &rcText, format1 | DT_VCENTER | DT_SINGLELINE | DT_END_ELLIPSIS);
}
::SelectObject(hDC, hOldFont);
diff --git a/SourceCode/Bond/Servo/BlButton.h b/SourceCode/Bond/Servo/BlButton.h
index 7b9bcea..f97f9af 100644
--- a/SourceCode/Bond/Servo/BlButton.h
+++ b/SourceCode/Bond/Servo/BlButton.h
@@ -53,6 +53,7 @@
void Flash(int ms);
void StopFlash();
BOOL IsFlash();
+ void SetTextRight();
private:
BOOL CustomBitBlt(HDC hDC, LPRECT lprc, CString& strBkgndBmp, int nFrame, int nAllFrame,
@@ -78,6 +79,7 @@
HICON m_hIcon[2];
int m_nIconWidth;
int m_nFlashState; // 闪烁状态,0:不闪;1和2为闪烁切换中
+ BOOL m_bTextRight;
public:
virtual void DrawItem(LPDRAWITEMSTRUCT /*lpDrawItemStruct*/);
diff --git a/SourceCode/Bond/Servo/Configuration.cpp b/SourceCode/Bond/Servo/Configuration.cpp
index d24527a..5df0f4b 100644
--- a/SourceCode/Bond/Servo/Configuration.cpp
+++ b/SourceCode/Bond/Servo/Configuration.cpp
@@ -92,6 +92,17 @@
return (int)texts.size();
}
+void CConfiguration::setFilterMode(int mode)
+{
+ WritePrivateProfileString(_T("Logcat"), _T("FilterMode"),
+ std::to_string(mode).c_str(), m_strFilepath);
+}
+
+int CConfiguration::getFilterMode()
+{
+ return GetPrivateProfileInt(_T("Logcat"), _T("FilterMode"), 0, m_strFilepath);
+}
+
int CConfiguration::getP2RemoteEqReconnectInterval()
{
return GetPrivateProfileInt(_T("P2"), _T("RemoteEqReconnectInterval"), 20, m_strFilepath);
diff --git a/SourceCode/Bond/Servo/Configuration.h b/SourceCode/Bond/Servo/Configuration.h
index 78fde46..1de8b08 100644
--- a/SourceCode/Bond/Servo/Configuration.h
+++ b/SourceCode/Bond/Servo/Configuration.h
@@ -20,6 +20,8 @@
void setLogcatIncludeRegex(BOOL bRegex);
BOOL isLogcatIncludeRegex();
int getCustomLogcatIncludeTexts(std::vector<std::string>& texts);
+ void setFilterMode(int mode);
+ int getFilterMode();
BOOL getPortParms(unsigned int index, BOOL& bEnable, int& type, int& mode,
int& cassetteType, int& transferMode, BOOL& bAutoChangeEnable);
diff --git a/SourceCode/Bond/Servo/LogEdit.cpp b/SourceCode/Bond/Servo/LogEdit.cpp
index 3b4742f..1b08345 100644
--- a/SourceCode/Bond/Servo/LogEdit.cpp
+++ b/SourceCode/Bond/Servo/LogEdit.cpp
@@ -21,12 +21,13 @@
BEGIN_MESSAGE_MAP(CLogEdit, CEdit)
ON_WM_CONTEXTMENU()
ON_WM_VSCROLL()
+ ON_WM_MOUSEWHEEL()
END_MESSAGE_MAP()
void CLogEdit::SetMaxLineCount(int line)
{
m_nMaxLines = line;
- m_nTrimLines = min(m_nMaxLines, 100);
+ m_nTrimLines = min(m_nMaxLines, 4000);
}
void CLogEdit::OnContextMenu(CWnd* pWnd, CPoint point)
@@ -60,6 +61,13 @@
CEdit::OnVScroll(nSBCode, nPos, pScrollBar);
}
+BOOL CLogEdit::OnMouseWheel(UINT nFlags, short zDelta, CPoint pt)
+{
+ // 每次滚动时检查是否还在底部
+ m_bAutoScroll = IsScrollBarAtBottom();
+ return CEdit::OnMouseWheel(nFlags, zDelta, pt);
+}
+
BOOL CLogEdit::IsScrollBarAtBottom()
{
SCROLLINFO si = { sizeof(si), SIF_ALL };
@@ -69,31 +77,41 @@
void CLogEdit::AppendText(const char* pszText)
{
- SetRedraw(FALSE);
+ SetRedraw(FALSE);
- // 裁剪逻辑
- int totalLines = GetLineCount();
- if (totalLines > m_nMaxLines) {
- // 获取要删除的字符范围
- int startChar = LineIndex(0); // 第0行首字符位置
- int endChar = LineIndex(m_nTrimLines); // 第N行首字符位置
+ // 剪切过多行
+ int totalLines = GetLineCount();
+ if (totalLines > m_nMaxLines) {
+ int startChar = LineIndex(0);
+ int endChar = LineIndex(m_nTrimLines);
+ if (startChar >= 0 && endChar > startChar) {
+ SetSel(startChar, endChar);
+ ReplaceSel(_T(""));
+ }
+ }
- if (startChar >= 0 && endChar > startChar) {
- SetSel(startChar, endChar);
- ReplaceSel(_T("")); // 删除前面行
- }
- }
+ // 保存当前选择
+ int start, end;
+ GetSel(start, end);
+ bool hasSelection = (start != end);
+ int endPos = GetWindowTextLength();
+ SetSel(endPos, endPos);
+ ReplaceSel(lpszText);
- int len = GetWindowTextLength();
- SetSel(len, len);
- ReplaceSel(pszText);
+ if (m_bAutoScroll && !hasSelection) {
+ LineScroll(GetLineCount());
+ }
- if (m_bAutoScroll) {
- LineScroll(GetLineCount());
- }
+ // 恢复选择
+ if (hasSelection) {
+ SetSel(start, end);
+ }
- SetRedraw(TRUE);
- Invalidate();
- UpdateWindow();
-}
\ No newline at end of file
+ SetRedraw(TRUE);
+
+ if (m_bAutoScroll && !hasSelection) {
+ Invalidate();
+ UpdateWindow();
+ }
+}
diff --git a/SourceCode/Bond/Servo/LogEdit.h b/SourceCode/Bond/Servo/LogEdit.h
index 3a3e823..617b444 100644
--- a/SourceCode/Bond/Servo/LogEdit.h
+++ b/SourceCode/Bond/Servo/LogEdit.h
@@ -20,5 +20,7 @@
DECLARE_MESSAGE_MAP()
afx_msg void OnContextMenu(CWnd* pWnd, CPoint point);
afx_msg void OnVScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar);
+public:
+ afx_msg BOOL OnMouseWheel(UINT nFlags, short zDelta, CPoint pt);
};
diff --git a/SourceCode/Bond/Servo/PageLog.cpp b/SourceCode/Bond/Servo/PageLog.cpp
index 4729c34..7fe626a 100644
--- a/SourceCode/Bond/Servo/PageLog.cpp
+++ b/SourceCode/Bond/Servo/PageLog.cpp
@@ -20,8 +20,9 @@
m_hbrBkgnd = nullptr;
m_pObserver = nullptr;
m_nLevel = 0;
- m_strIncludeText = _T("");
- m_bIncludeRegex = FALSE;
+ m_strFilterText = _T("");
+ m_bRegex = FALSE;
+ m_filterMode = FilterMode::Include;
}
CPageLog::~CPageLog()
@@ -70,19 +71,24 @@
&& pAny->getIntValue("exCode", level)) {
if (level >= m_nLevel) {
CString strText = pszLogMsg;
- BOOL bInclude = TRUE;
- if (!m_strIncludeText.IsEmpty()) {
- if (!m_bIncludeRegex) {
- bInclude = (strText.Find(m_strIncludeText) >= 0);
+ BOOL bMatch = TRUE;
+ if (!m_strFilterText.IsEmpty()) {
+ if (!m_bRegex) {
+ bMatch = (strText.Find(m_strFilterText) >= 0);
}
else {
- bInclude = std::regex_search((LPTSTR)(LPCTSTR)strText,
- std::regex((LPTSTR)(LPCTSTR)m_strIncludeText));
+ CString strTemp = strText;
+ strTemp.TrimRight();
+ bMatch = std::regex_match((LPTSTR)(LPCTSTR)strTemp,
+ std::regex((LPTSTR)(LPCTSTR)m_strFilterText));
+ }
+ if (m_filterMode == FilterMode::Exclude) {
+ bMatch = !bMatch;
}
}
- if (bInclude) {
+ if (bMatch) {
strText.Replace("\n", "\r\n");
AppendLog(level, (LPTSTR)(LPCTSTR)strText);
}
@@ -110,9 +116,12 @@
// 缓存
m_nLevel = theApp.m_model.m_configuration.getLogcatLevel();
- theApp.m_model.m_configuration.getLogcatIncludeText(m_strIncludeText);
- m_bIncludeRegex = theApp.m_model.m_configuration.isLogcatIncludeRegex();
+ theApp.m_model.m_configuration.getLogcatIncludeText(m_strFilterText);
+ m_bRegex = theApp.m_model.m_configuration.isLogcatIncludeRegex();
theApp.m_model.m_configuration.getCustomLogcatIncludeTexts(m_customIncludeTexts);
+ m_customIncludeTexts.clear();
+ m_customIncludeTexts.push_back("包含");
+ m_customIncludeTexts.push_back("排除");
// Level
@@ -135,6 +144,9 @@
strIcon1, IMAGE_ICON, 24, 24,
LR_LOADFROMFILE | LR_DEFAULTCOLOR | LR_CREATEDIBSECTION | LR_DEFAULTSIZE);
m_btnInclude.SetIcon(hIcon, hIcon, 24);
+ m_filterMode = (FilterMode)theApp.m_model.m_configuration.getFilterMode();
+ m_btnInclude.SetTextRight();
+ m_btnInclude.SetWindowText(m_filterMode == FilterMode::Include ? "包含" : "排除");
{
HMENU hMenu = LoadMenu(AfxGetInstanceHandle(), MAKEINTRESOURCEA(IDR_MENU_INCLUDE));
@@ -143,19 +155,19 @@
int i = 0;
for (auto& item : m_customIncludeTexts) {
i++;
- InsertMenu(hSubMenu, 0, MF_BYPOSITION, 0x1998 + i, item.c_str());
+ InsertMenu(hSubMenu, i, MF_BYPOSITION, 0x1998 + i, item.c_str());
m_btnInclude.SetMenu(hMenu);
}
}
- SetDlgItemText(IDC_EDIT_INCLUDE, m_strIncludeText);
+ SetDlgItemText(IDC_EDIT_INCLUDE, m_strFilterText);
CButton* pCheckBox = (CButton*)GetDlgItem(IDC_CHECK_REGEX);
- pCheckBox->SetCheck(m_bIncludeRegex ? BST_CHECKED : BST_UNCHECKED);
+ pCheckBox->SetCheck(m_bRegex ? BST_CHECKED : BST_UNCHECKED);
// 内容
- m_logEdit.SetMaxLineCount(500);
+ m_logEdit.SetMaxLineCount(6000);
m_logEdit.SetLimitText(-1);
Resize();
@@ -290,28 +302,22 @@
void CPageLog::OnButtonIncludeMenuClicked(NMHDR* pNMHDR, LRESULT* pResult)
{
BLBUTTON_NMHDR* pblbNmhdr = reinterpret_cast<BLBUTTON_NMHDR*>(pNMHDR);
- int position = (int)pblbNmhdr->dwData;
- std::string& strInclude = m_customIncludeTexts.at(position);
- SetDlgItemText(IDC_EDIT_INCLUDE, strInclude.c_str());
- CButton* pCheckBox = (CButton*)GetDlgItem(IDC_CHECK_REGEX);
- m_bIncludeRegex = FALSE;
- pCheckBox->SetCheck(BST_UNCHECKED);
-
- theApp.m_model.m_configuration.setLogcatIncludeRegex(m_bIncludeRegex);
- theApp.m_model.m_configuration.setLogcatIncludeText(m_strIncludeText);
+ m_filterMode = (FilterMode)pblbNmhdr->dwData;
+ theApp.m_model.m_configuration.setFilterMode((int)m_filterMode);
+ m_btnInclude.SetWindowText(m_filterMode == FilterMode::Include ? "包含" : "排除");
*pResult = 0;
}
void CPageLog::OnEnChangeEditInclude()
{
- GetDlgItemText(IDC_EDIT_INCLUDE, m_strIncludeText);
- theApp.m_model.m_configuration.setLogcatIncludeText(m_strIncludeText);
+ GetDlgItemText(IDC_EDIT_INCLUDE, m_strFilterText);
+ theApp.m_model.m_configuration.setLogcatIncludeText(m_strFilterText);
}
void CPageLog::OnBnClickedCheckRegex()
{
CButton* pCheckBox = (CButton*)GetDlgItem(IDC_CHECK_REGEX);
- m_bIncludeRegex = pCheckBox->GetCheck();
- theApp.m_model.m_configuration.setLogcatIncludeRegex(m_bIncludeRegex);
+ m_bRegex = pCheckBox->GetCheck();
+ theApp.m_model.m_configuration.setLogcatIncludeRegex(m_bRegex);
}
diff --git a/SourceCode/Bond/Servo/PageLog.h b/SourceCode/Bond/Servo/PageLog.h
index 391f64d..4e373d2 100644
--- a/SourceCode/Bond/Servo/PageLog.h
+++ b/SourceCode/Bond/Servo/PageLog.h
@@ -7,6 +7,12 @@
#define ID_MSG_LOGDLG_HIDE WM_USER + 1023
+
+enum class FilterMode {
+ Include, // 只保留匹配行
+ Exclude // 排除匹配行
+};
+
// CPageLog 对话框
class CPageLog : public CDialogEx
@@ -29,14 +35,15 @@
HBRUSH m_hbrBkgnd;
IObserver* m_pObserver;
int m_nLevel;
- CString m_strIncludeText;
- BOOL m_bIncludeRegex;
+ CString m_strFilterText;
+ BOOL m_bRegex;
std::vector<std::string> m_customIncludeTexts;
private:
CBlButton m_btnLevel;
CBlButton m_btnInclude;
CLogEdit m_logEdit;
+ FilterMode m_filterMode;
// 对话框数据
diff --git a/SourceCode/Bond/Servo/Servo.rc b/SourceCode/Bond/Servo/Servo.rc
index 3cb2416..63b6347 100644
--- a/SourceCode/Bond/Servo/Servo.rc
+++ b/SourceCode/Bond/Servo/Servo.rc
Binary files differ
diff --git a/SourceCode/Bond/Servo/ServoDlg.cpp b/SourceCode/Bond/Servo/ServoDlg.cpp
index de985ad..26b9e62 100644
--- a/SourceCode/Bond/Servo/ServoDlg.cpp
+++ b/SourceCode/Bond/Servo/ServoDlg.cpp
@@ -285,6 +285,10 @@
SetIcon(m_hIcon, FALSE); // 设置小图标
+ // model init
+ theApp.m_model.init();
+
+
// 菜单
CMenu menu;
menu.LoadMenu(IDR_MENU_APP);
@@ -353,9 +357,6 @@
int height = GetSystemMetrics(SM_CYSCREEN);
MoveWindow((width - rcWnd.Width()) / 2, 0, rcWnd.Width(), rcWnd.Height(), TRUE);
-
- // model init
- theApp.m_model.init();
SetTimer(TIMER_ID_CREATE_TERMINAL, 3000, nullptr);
diff --git a/SourceCode/Bond/x64/Debug/Res/logcat_include.ico b/SourceCode/Bond/x64/Debug/Res/logcat_include.ico
index 275a472..9608f1b 100644
--- a/SourceCode/Bond/x64/Debug/Res/logcat_include.ico
+++ b/SourceCode/Bond/x64/Debug/Res/logcat_include.ico
Binary files differ
--
Gitblit v1.9.3