O que é esse controle?Caixa de grupo ou não!
Pergunta
Apenas curioso sobre o controle mostrado abaixo, a linha reta com o rótulo ao lado.Tentei encontrar um controle semelhante para ele, mas não havia nenhuma configuração de caixa de grupo, então, em vez disso, fiz apenas um GroupBox com uma altura de 2 que o replica.
Mas existe um controle ou configuração real para fazer isso?E como é chamado o controle real?
Solução
Spy ++ nos diz que esses são, na verdade, dois controles STATIC
(semelhante a um Label
em WinForms).
-
O primeiro é simplesmente um controle de texto estático regular que diz "Página inicial".
-
O segundo tem o estilo
SS_ETCHEDHORZ
definido, que faz com que seja desenhada como uma linha 3D. Infelizmente, a capacidade de definir esse estilo não é exposta a nós no WinForms.
Como você observou na pergunta, existem alguns hacks / soluções alternativas que nos permitem obter uma aparência semelhante, como compactar verticalmente um controle GroupBox
ou substituir o método OnPaint
de um controle Label
e usar a classe ControlPaint
para desenhar um fronteira. Eles funcionam, mas nunca gostei deles.
Mas você pode realmente definir o estilo SS_ETCHEDHORZ
sozinho para que possa replicar a IU nativa com exatidão. Aqui está uma pequena aula que faz exatamente isso. Adicione-o ao seu projeto, compile, e você verá um novo controle aparecer na sua caixa de ferramentas chamado "HorizontalRule". Use-o como faria com qualquer outro controle!
public class HorizontalRule : Control
{
private const int FixedHeight = 2;
private const int WS_CHILD = 0x40000000;
private const int WS_VISIBLE = 0x10000000;
private const int SS_ETCHEDHORZ = 0x00000010;
private const int SS_ETCHEDVERT = 0x00000011;
protected override CreateParams CreateParams
{
get
{
CreateParams cp = base.CreateParams;
cp.ClassName = "STATIC";
cp.Style = WS_CHILD | SS_ETCHEDHORZ;
if (this.Visible)
{
cp.Style |= WS_VISIBLE;
}
return cp;
}
}
protected override void SetBoundsCore(int x, int y, int width, int height, BoundsSpecified specified)
{
height = FixedHeight;
base.SetBoundsCore(x, y, width, height, specified);
}
}
Você também pode encontrar informações mais detalhadas e código de amostra adicional aqui no CodeProject .
Outras dicas
Tive o mesmo problema alguns anos atrás e acabei traçando uma linha para esse propósito.
Na verdade, eu até usei uma imagem de linha fixa com largura suficientemente longa para que pudesse ser usada em todos os casos, mostrando a parte necessária (largura) da imagem.
Esta solução tem funcionado bem para mim desde então.