win32编程实现文本编辑器,不使用任何控件,本人完成,现在当鼠标左键按下,并且移动时,选中所经过的文本字符,并让这些字符高亮显示,例如系统自带的NotePad一样,现在是鼠标移动的起始位置和终止位置本人都能正确的得到,关键就是本人该怎么重绘这个区域之间的字符?分不多了,请大家帮帮,谢谢!
解决方案
15
// this four variable mean the select area int selectAreaX1 = 0; int selectAreaY1 = 0; int selectAreaX2 = 0; int selectAreaY2 = 0; void DrawSelectArea(HDC hDC, RECT rect) // color the select area { HBRUSH hBrush; hBrush = CreateSolidBrush(RGB(255,255,0)); SetDCBrushColor(hDC,RGB(255, 255, 0)); RECT rectSelect; SIZE size1, size2; GetTextExtentPoint(hDC, data[selectAreaY2], selectAreaX2, &size2); GetTextExtentPoint(hDC, data[selectAreaY1], selectAreaX1, &size1); // calculate the select rect area and Fill it. if (selectAreaY1 < selectAreaY2) { rectSelect.bottom = 16 * (selectAreaY2 + 1); rectSelect.left = 0; rectSelect.right = size2.cx + 40; rectSelect.top = 16 * selectAreaY2; FillRect(hDC, &rectSelect, hBrush); rectSelect.bottom = 16 * (selectAreaY2); rectSelect.left = 0; rectSelect.right = rect.right; rectSelect.top = 16 * (selectAreaY1 + 1); FillRect(hDC, &rectSelect, hBrush); rectSelect.bottom = 16 * (selectAreaY1 + 1); rectSelect.left = size1.cx + 40; rectSelect.right = rect.right; rectSelect.top = 16 * (selectAreaY1); FillRect(hDC, &rectSelect, hBrush); } if (selectAreaY1 > selectAreaY2) { rectSelect.bottom = 16 * (selectAreaY1+1); rectSelect.left = 0; rectSelect.right = size1.cx + 40; rectSelect.top = 16 * selectAreaY1; FillRect(hDC, &rectSelect, hBrush); rectSelect.bottom = 16 * (selectAreaY1); rectSelect.left = 0; rectSelect.right = rect.right; rectSelect.top = 16 * (selectAreaY2+1); FillRect(hDC, &rectSelect, hBrush); rectSelect.bottom = 16 * (selectAreaY2+1); rectSelect.left = size2.cx + 40; rectSelect.right = rect.right; rectSelect.top = 16 * (selectAreaY2); FillRect(hDC, &rectSelect, hBrush); } if (selectAreaY1 == selectAreaY2) { if (selectAreaX1 > selectAreaX2) { rectSelect.bottom = 16 * (selectAreaY1+1); rectSelect.left = size2.cx + 40; rectSelect.right = size1.cx + 40; rectSelect.top = 16 * (selectAreaY1); FillRect(hDC, &rectSelect, hBrush); } if (selectAreaX1 < selectAreaX2) { rectSelect.bottom = 16 * (selectAreaY1+1); rectSelect.left = size1.cx + 40; rectSelect.right = size2.cx + 40; rectSelect.top = 16 * (selectAreaY1); FillRect(hDC, &rectSelect, hBrush); } } DeleteObject(hBrush); }
不知道是不是你想要的..这个好像选中区域中的空白部分也会被重绘,
5
参考Notepad++源代码。
5
1. 在鼠标按下和移动是记录选择区域, 可以以[选中标志][起始行、列]、[终止行、列]的方式保存
原因是向上选中和向下选中时,选中起始不同, 所以最好保存一下向上选中时的 [起始行、列]和向下选中时的[起始行、列]
2. 描画时, 确认数据能否和选择区域有交叉, 假如有交叉, 给交叉的部分画个实体矩形, 然后显示文字。
原因是向上选中和向下选中时,选中起始不同, 所以最好保存一下向上选中时的 [起始行、列]和向下选中时的[起始行、列]
2. 描画时, 确认数据能否和选择区域有交叉, 假如有交叉, 给交叉的部分画个实体矩形, 然后显示文字。
15
描画矩形
一行选中情况 ***********<*************>,”<>”内为选中字符串
一行选中情况 ***********<*************>,”<>”内为选中字符串
int iPos = 0; int iTemp = 0; CRect Rect; pDC ->SetBkMode(TRANSPARENT); // normal 没选中字体也能设置背景色 iPos = point.x; iTemp = DrawSelInfo.iStPos - DrawData.iStPos; Rect = CRect(iPos, point.y, iPos + iTemp * TextInfo.iWidth, point.y + TextInfo.iLineWidth); pDC ->FillRect(Rect, pBGBrush); // select iPos += iTemp * TextInfo.iWidth; Rect = CRect(iPos, point.y, iPos + (strText.GetLength() - iTemp) * TextInfo.iWidth, point.y + TextInfo.iLineWidth); pDC ->FillRect(Rect, &m_SelectBrush); pDC ->TextOut(point.x, point.y, strText);