Sei sulla pagina 1di 2

Delphi: Cuidados ao usar o Evento OnExit

comum fazermos uso do evento OnExit quando queremos validar o contedo de um Edit. E essa pode ser uma boa prtica quando necessitamos verificar o que foi digitado apenas quando o usurio terminar de fazer a entrada de dados, como, por exemplo, um Edit que vai receber o CPF ou CNPJ. Ao colocarmos um cdigo qualquer no evento OnExit ele sempre ser executado quando o usurio sair do Edit, o que acontece quando ele pressiona a tecla TAB, clica com o mouse em um outro Edit ou pressiona um boto OK, por exemplo. No entanto, existem algumas situaes especiais em que o evento OnExit no gerado. Quer um exemplo? Voc est no Edit e, ao invs de clicar no boto OK, voc pressiona as teclas ALT + O (considerando que o boto OK tem a tecla O como atalho). como se voc tivesse pressionado o boto OK, porm, sem perder o foco que est no Edit. S mais um exemplo: Os botes do tipo SpeedButton no recebem foco, ento, mesmo que clique com o mouse sobre um SpeedButton, o foco continuar no Edit e, conseqentemente, o evento OnExit no ser gerado. E a soluo ????? A soluo para esse pequeno inconveniente simples. Basta voc colocar o seguinte cdigo no evento OnClick do boto. procedure TForm1.Button1Click(Sender: TObject); begin ActiveControl := nil; end; Suponhamos que voc possua 2 Edits em um formulrio. Supondo tambm que voc queira dar alguma informao ao usurio da aplicao logo depois que ele sair do Edit1 voc faz: procedure TForm1.Edit1Exit(Sender: TObject); begin MessageDlg("Mensagem...", mtInformation, [mbOk], 0); end; A princpio est tudo ok, ou melhor, parece estar tudo ok. Se voc altera o foco para o outro Edit atravs do pressionamento da tecla TAB, tudo bem. Mas experimente alterar o foco clicando com o mouse sobre o Edit2. Neste segundo caso a mensagem ser exibida normalmente. Mas ao fechar o dialogo onde aparece a mensagem, o foco simplesmente se perde. Para setar o foco no Edit2 necessrio clicar novamente sobre ele. Isso poderia no problema nenhum at que seu usurio experimente esta situao. Nada que ele digitar ser acatado. Mas existe uma maneira fcil de resolver o problema. Basta voc cancelar o foco e forar uma reentrada no componente Edit2. Como fazer isso? Veja o cdigo:

procedure TForm1.Edit1Exit(Sender: TObject); begin MessageDlg("Mensagem...", mtInformation, [mbOk], 0); // cancela o foco e fora novamente a entrada ActiveControl := nil; PostMessage(Edit2.Handle, WM_SETFOCUS, 0, 0); Edit2.SetFocus; end; Porm, voc nunca ter certeza se o usurio clicou foi no Edit2. Ento temos que criar uma rotina genrica que leva o foco para qualquer outro controle: procedure TForm1.Edit1Exit(Sender: TObject); var Ctrl: TWinControl; begin MessageDlg("Mensagem...", mtInformation, [mbOk], 0); // cancela o foco e fora novamente a entrada Ctrl := ActiveControl; ActiveControl := nil; PostMessage(TWinControl(Ctrl).Handle, WM_SETFOCUS, 0, 0); TWinControl(Ctrl).SetFocus; end; Observe que antes de cancelar o foco com ActiveControl := nil, salvamos qual o controle que detm o foco fazendo Ctrl := ActiveControl. Depois enviamos uma mensagem ao controle que detinha o foco, forando-o a receber o foco novamente. E Pronto!!!!!!!

Potrebbero piacerti anche