int CxEdit::GotoEnd(BOOL bScroll /*= TRUE*/)
{
const int length = GetWindowTextLength();
SetSel(length, length, !bScroll); // end of edit text
return LineFromChar(length);
}
//////////////////////////////////////////////////////////////////////////////
// This function is based on Daniel Lohmann's article "CEditLog - fast logging
// into an edit control with cout" at http://www.codeproject.com
void CLogEditCtrl::AddLine(LPCTSTR pszMsg, int iLen)
{
int iMsgLen = (iLen == -1) ? _tcslen(pszMsg) : iLen;
if (iMsgLen == 0)
return;
#ifdef _DEBUG
if (pszMsg[iMsgLen - 1] == _T('\n'))
ASSERT( iMsgLen >= 2 && pszMsg[iMsgLen - 2] == _T('\r') );
#endif
// Get Edit contents dimensions and cursor position
int iStartChar, iEndChar;
GetSel(iStartChar, iEndChar);
int iWndTxtLen = GetWindowTextLength();
if (iStartChar == iWndTxtLen && iWndTxtLen == iEndChar)
{
// The cursor resides at the end of text
SCROLLINFO si;
si.cbSize = sizeof si;
si.fMask = SIF_ALL;
if (m_bAutoScroll && GetScrollInfo(SB_VERT, &si) && si.nPos >= (int)(si.nMax - si.nPage + 1))
{
// Not scrolled away
SafeAddLine(iWndTxtLen, iMsgLen, pszMsg, iStartChar, iEndChar);
if (m_bAutoScroll && !IsWindowVisible())
ScrollToLastLine();
}
else
{
// Reduce flicker by ignoring WM_PAINT
m_bNoPaint = true;
BOOL bIsVisible = IsWindowVisible();
if (bIsVisible)
SetRedraw(FALSE);
// Remember where we are
int nFirstLine = !m_bAutoScroll ? GetFirstVisibleLine() : 0;
// Select at the end of text and replace the selection
// This is a very fast way to add text to an edit control
SafeAddLine(iWndTxtLen, iMsgLen, pszMsg, iStartChar, iEndChar);
SetSel(iStartChar, iEndChar, TRUE); // Restore our previous selection
if (!m_bAutoScroll)
LineScroll(nFirstLine - GetFirstVisibleLine());
else
ScrollToLastLine();
m_bNoPaint = false;
if (bIsVisible){
SetRedraw();
if (m_bRichEdit)
Invalidate();
}
}
}
else
{
// We should add the text anyway...
// Reduce flicker by ignoring WM_PAINT
m_bNoPaint = true;
BOOL bIsVisible = IsWindowVisible();
if (bIsVisible)
SetRedraw(FALSE);
// Remember where we are
int nFirstLine = !m_bAutoScroll ? GetFirstVisibleLine() : 0;
if (iStartChar != iEndChar)
{
// If we are currently selecting some text, we have to find out
// if the caret is near the beginning of this block or near the end.
// Note that this does not always work. Because of the EM_CHARFROMPOS
// message returning only 16 bits this will fail if the user has selected
// a block with a length dividable by 64k.
// NOTE: This may cause a lot of terrible CRASHES within the RichEdit control when used for a RichEdit control!?
// To reproduce the crash: click in the RE control while it's drawing a line an start a selection!
if (!m_bRichEdit){
CPoint pt;
::GetCaretPos(&pt);
int nCaretPos = CharFromPos(pt);
if (abs((iStartChar % 0xffff - nCaretPos)) < abs((iEndChar % 0xffff - nCaretPos)))
{
nCaretPos = iStartChar;
iStartChar = iEndChar;
iEndChar = nCaretPos;
}
}
}
// Note: This will flicker, if someone has a good idea how to prevent this - let me know
// Select at the end of text and replace the selection
// This is a very fast way to add text to an edit control
//.........这里部分代码省略.........
//.........这里部分代码省略.........
case WM_COMMAND: // Item do menu, tecla de atalho ou controle ativado
{
// Verifica bit menos significativo de wParam (ID’s)
switch(LOWORD(wParam))
{
case IDM_ABRIR:
{
// Se arquivo ainda não foi aberto
if(hFile == NULL)
{
// Abre/cria arquivo
hFile = CreateFile("dados.txt", GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
// Verifica se identificador do arquivo é válido
if(hFile == INVALID_HANDLE_VALUE)
MessageBox(hWnd, "Erro ao abrir/criar arquivo.", "Erro!", MB_ICONERROR | MB_OK);
else // Arquivo é válido
{
MessageBox(hWnd, "Arquivo aberto/criado.", "Aviso!", MB_ICONINFORMATION | MB_OK);
SendMessage(hWnd, WM_SETTEXT, (WPARAM)0, (LPARAM)"Arquivo aberto/criado.");
// Cria botões para usuário selecionar opção
hWndBotao = CreateWindowEx(WS_EX_CLIENTEDGE, "BUTTON", "Clique aqui!", WS_CHILD | WS_VISIBLE, 10, 10, 100, 30, hWnd, (HMENU)IDC_BOTAO, NULL, NULL);
}
}
} break;
case IDM_SALVAR:
{
if(hFile != INVALID_HANDLE_VALUE) // Arquivo está aberto
{
// Obtém quantidade de caracteres da caixa de texto
int tam = GetWindowTextLength(hWndTexto);
// Obtém conteúdo da caixa de texto, alocando memória para os dados
// (alocação no modo Windows)
LPSTR lpstrBuffer = (LPSTR)GlobalAlloc(GPTR, tam + 1);
GetWindowText(hWndTexto, lpstrBuffer, tam + 1);
// Armazena quantos bytes foram escritos no arquivo
DWORD dwBytesEscritos;
// Modifica posição do arquivo para o início
SetFilePointer(hFile, NULL, NULL, FILE_BEGIN);
// Grava conteúdo da caixa de texto no arquivo
WriteFile(hFile, lpstrBuffer, tam, &dwBytesEscritos, NULL);
// Define fim do arquivo
SetEndOfFile(hFile);
// Libera memória dos dados
GlobalFree(lpstrBuffer);
MessageBox(hWnd, "Conteúdo escrito no arquivo.", "Aviso!", MB_ICONINFORMATION | MB_OK);
}
else // Arquivo não foi aberto
MessageBox(hWnd, "Erro ao escrever no arquivo.", "Erro!", MB_ICONERROR | MB_OK);
} break;
case IDM_FECHAR:
{
// Se o arquivo está aberto, fecha
if(hFile)
{
//.........这里部分代码省略.........
{
MessageBox(hwnd, "Admin access required. Some features may not work properly. \n\n"
"**If on Vista (or Server 2008), choose the \"Run as administrator\" option.",
"Admin access required.", MB_OK);
break;
}
}
break;
case WM_COMMAND:
switch(LOWORD(wParam))
{
/* In case of SAVE */
case IDC_ADD:
{
int chd = 0;
int len;
if(config_inst.admin_access == 0)
{
MessageBox(hwnd, "Unable to edit configuration. "
"Admin access required.",
"Error Saving.", MB_OK);
break;
}
/** Getting values from the user (if chosen save)
* We should probably create another function for it...
**/
/* Getting server ip */
len = GetWindowTextLength(GetDlgItem(hwnd, UI_SERVER_TEXT));
if(len > 0)
{
char *buf;
/* Allocating buffer */
buf = (char*)GlobalAlloc(GPTR, len + 1);
if(!buf)
{
exit(-1);
}
GetDlgItemText(hwnd, UI_SERVER_TEXT, buf, len + 1);
/* If auth key changed, set it */
if(strcmp(buf, config_inst.server) != 0)
{
if(set_ossec_server(buf, hwnd))
{
chd = 1;
}
}
else
{
GlobalFree(buf);
}
}
/* Getting auth key */
len = GetWindowTextLength(GetDlgItem(hwnd, UI_SERVER_AUTH));
if(len > 0)
//.........这里部分代码省略.........
break;
// We accept this message so we can set a minimum window size. This only sets the users
// tracking size. The window itself can always be resized smaller programmatically unless
// you restrict it in WM_WINDOWPOSCHANGING/WM_WINDOWPOSCHANGED.
case WM_GETMINMAXINFO:
{
LPMINMAXINFO lpInfo = (LPMINMAXINFO)lParam;
if(lpInfo)
lpInfo->ptMinTrackSize.x = 250, lpInfo->ptMinTrackSize.y = 300;
}
return 0;
// These next two messages are better to use rather than WM_MOVE/WM_SIZE.
// Remember WM_MOVE/WM_SIZE are from 16bit windows. In 32bit windows the window
// manager only sends these two messages and the DefWindowProc() handler actually
// accepts them and converts them to WM_MOVE/WM_SIZE.
//
// We accept this so we can scale our controls to the client size.
case WM_WINDOWPOSCHANGING:
case WM_WINDOWPOSCHANGED:
{
HDWP hDWP;
RECT rc;
// Create a deferred window handle.
if(hDWP = BeginDeferWindowPos(4))
{
// Deferring 4 child controls
GetClientRect(hWnd, &rc);
// Calculate the size needed for the static text at the top
RECT rcText = { 10, 10, rc.right - 20, 0 } ;
CalcWindowTextSize(GetDlgItem(hWnd, IDC_LBLINFO), &rcText);
// Defer each window move/size until end and do them all at once.
hDWP = DeferWindowPos(hDWP, GetDlgItem(hWnd, IDC_LBLINFO), NULL,
10, 10, rc.right - 20, rcText.bottom,
SWP_NOZORDER | SWP_NOREDRAW);
// Move/Size the listbox
hDWP = DeferWindowPos(hDWP, GetDlgItem(hWnd, IDC_LSTCUSTOM), NULL,
10, rcText.bottom + 20, rc.right - 20, rc.bottom - rcText.bottom - 75,
SWP_NOZORDER | SWP_NOREDRAW);
// Move/Size the input box
hDWP = DeferWindowPos(hDWP, GetDlgItem(hWnd, IDC_INPUTBOX), NULL,
10, rc.bottom - 40, rc.right - 90, 30,
SWP_NOZORDER | SWP_NOREDRAW);
// Move/Size the send button
hDWP = DeferWindowPos(hDWP, GetDlgItem(hWnd, IDCANCEL), NULL,
(rc.right) - 70, rc.bottom - 40, 60, 30,
SWP_NOZORDER | SWP_NOREDRAW);
// Resize all windows under the deferred window handled at the same time.
EndDeferWindowPos(hDWP);
// We told DeferWindowPos not to redraw the controls so we can redraw
// them here all at once.
RedrawWindow(hWnd, NULL, NULL, RDW_INVALIDATE | RDW_ALLCHILDREN |
RDW_ERASE | RDW_NOFRAME | RDW_UPDATENOW);
}
}
return 0;
// Handle the notifications of button presses.
case WM_COMMAND:
// If it was a button press and it came from our button.
if(wParam == MAKELONG(IDCANCEL, BN_CLICKED) ||
(GetFocus() == inputhwnd) && (0x8000 & GetKeyState(VK_RETURN)))
{
// process typed command
if(GetWindowTextLength(inputhwnd) == 0)
break;
char str[512];
SendMessage(inputhwnd, WM_GETTEXT, (WPARAM)512, (LPARAM)str);
SendMessage(inputhwnd, WM_SETTEXT, 0, (LPARAM)"");
RunCommand(str, 0);
SetFocus(inputhwnd);
}
else if(HIWORD(wParam) == LBN_DBLCLK)
{
}
break;
case WM_DESTROY:
// We post a WM_QUIT when our window is destroyed so we break the main message loop.
sampDisconnect(0);
PostQuitMessage(0);
break;
}
// Not a message we wanted? No problem hand it over to the Default Window Procedure.
return DefWindowProc(hWnd, uMsg, wParam, lParam);
}
请发表评论