Winforms 레이블이 투명하고 싶지 않은 이유는 무엇입니까?
-
03-07-2019 - |
문제
라벨의 백색을 투명하게 설정할 수없는 이유는 무엇입니까? 전에 해본 적이 있지만 이제는 원하지 않습니다 ...
새로운 USERCONTROL을 만들었고 ProgressBar와 레이블을 추가했습니다. 레이블의 백색을 투명하게 설정하면 여전히 회색입니다 =/ 왜 이거야?
내가 원했던 것은 텍스트가 진행된 "The ProgressBar ...
해결책
Winforms는 실제로 투명한 컨트롤을 지원하지 않지만 투명한 제어를 직접 만들 수 있습니다. 여기에서 내 대답을 참조하십시오.
귀하의 경우 진행률 표시 줄을 서브 클래스하고 OnPaint 메소드를 무시하여 진행률 표시 줄에 텍스트를 그립니다.
다른 팁
프로젝트에 새 클래스를 추가하고 아래에 표시된 코드를 게시하십시오. 짓다. 새 컨트롤을 도구 상자 상단에서 양식으로 떨어 뜨립니다.
using System;
using System.Windows.Forms;
public class TransparentLabel : Label {
public TransparentLabel() {
this.SetStyle(ControlStyles.Opaque, true);
this.SetStyle(ControlStyles.OptimizedDoubleBuffer, false);
}
protected override CreateParams CreateParams {
get {
CreateParams parms = base.CreateParams;
parms.ExStyle |= 0x20; // Turn on WS_EX_TRANSPARENT
return parms;
}
}
}
가장 간단한 솔루션은 다음과 같습니다.
시각적 편집기 또는 양식의 생성자에서 배경색을 투명성으로 설정하십시오.
this.label1.BackColor = System.Drawing.Color.Transparent;
라벨의 부모 속성을 설정하여 텍스트 뒤에서 볼 수 있도록 제어하십시오. 이는 양식 생성자 또는로드 방법으로 수행 할 수 있습니다.
this.label1.parent = progressbar1;
Directx에서와 같이 이것이 진정한 투명성이 아니라는 것은 사실입니다. 디스플레이에 표시된 결과는 두 레이어로만 구성됩니다. 이 접근법으로 두 개 이상의 레이어를 요약 할 수 없습니다 (각 층은 알파 매개 변수로 정의 된 자체 투명성을 갖습니다). 그러나 WinForms 프로그래밍에서 만날 수있는 많은 실제 상황에 적합합니다.
일반 레이블이 아닌 LinkLabel을 사용하십시오
private void MakeTransparentLabel(System.Windows.Forms.LinkLabel LinkLabel)
{
this.MakeTransparentLabel(LinkLabel, Color.White);
}
private void MakeTransparentLabel(System.Windows.Forms.LinkLabel LinkLabel, Color ForeColor)
{
LinkLabel.ForeColor = ForeColor;
LinkLabel.LinkColor = ForeColor;
LinkLabel.VisitedLinkColor = ForeColor;
LinkLabel.ActiveLinkColor = ForeColor;
LinkLabel.DisabledLinkColor = ForeColor;
LinkLabel.LinkArea = new LinkArea(0, 0);
LinkLabel.LinkBehavior = LinkBehavior.NeverUnderline;
LinkLabel.Cursor = Cursors.Arrow;
LinkLabel.BackColor = Color.Transparent;
}
private void SetTransparentLabelText(System.Windows.Forms.LinkLabel LinkLabel, string Text)
{
if (string.IsNullOrEmpty(Text)) { LinkLabel.Text = " "; return; }
LinkLabel.Text = Text;
}
Windows 애플리케이션 설계에 집중하려면 WPF를 사용하는 것이 좋습니다.
WPF에서 컨트롤을 투명하게 만드는 것은 매우 쉽습니다.
<TextBox Width="200" Height="40" Opacity="0.5"/>
회전 된 텍스트를 표시하는 얼마 전에 쓴 투명한 컨트롤이 있습니다. 대부분의 코드는 여기, IIRC에도 불구하고 나는 그것을 작동시키기 위해 약간의 조정을해야했습니다.
using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Text;
using System.Linq;
using System.Windows.Forms;
namespace MyNamespace
{
public partial class RotatedText : UserControl
{
private readonly Timer _invalidationTimer;
private const int WS_EX_TRANSPARENT = 0x00000020;
public RotatedText()
{
this.SetStyle(ControlStyles.SupportsTransparentBackColor, true);
InitializeComponent();
_invalidationTimer = new Timer {Interval = 500, Enabled = true};
_invalidationTimer.Tick += TickHandler;
}
[Browsable(true)]
[DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
[Category("Appearance")]
[Description("Text which appears in control")]
public string Text { get; set; }
#region Transparent background
protected override CreateParams CreateParams
{
get
{
CreateParams cp = base.CreateParams;
cp.ExStyle |= WS_EX_TRANSPARENT;
return cp;
}
}
private void TickHandler(object sender, EventArgs e)
{
InvalidateEx();
}
private void InvalidateEx()
{
if (Parent != null)
Parent.Invalidate(Bounds, false);
else
Invalidate();
}
protected override void OnPaintBackground(PaintEventArgs e)
{
//Intentionally do nothing - stops background from drawing
//base.OnPaintBackground(e);
}
#endregion
//Rotate text and draw
protected override void OnPaint(PaintEventArgs e)
{
double angleRadians = Math.Atan2(Height, Width);
float angleDegrees = -1*(float) (angleRadians*180/Math.PI);
angleDegrees *= 0.9f;
e.Graphics.RotateTransform(angleDegrees, MatrixOrder.Append);
e.Graphics.TranslateTransform(20, Height - 75, MatrixOrder.Append);
e.Graphics.TextRenderingHint = TextRenderingHint.AntiAliasGridFit;
Font font = new Font("Ariel", 50);
e.Graphics.DrawString(Text, font, Brushes.Gray, 1, 2); //Shadow
e.Graphics.DrawString(Text, font, Brushes.Red, 0, 0);
}
}
}
이것은 매우 간단한 솔루션이며 훌륭합니다.
public class MyLabel : Label
{
private bool fTransparent = false;
public bool Transparent
{
get { return fTransparent; }
set { fTransparent = value; }
}
public MyLabel() : base()
{
}
protected override CreateParams CreateParams
{
get
{
if (fTransparent)
{
CreateParams cp = base.CreateParams;
cp.ExStyle |= 0x00000020; //WS_EX_TRANSPARENT
return cp;
}
else return base.CreateParams;
}
}
protected override void WndProc(ref Message m)
{
if (fTransparent)
{
if (m.Msg != 0x14 /*WM_ERASEBKGND*/ && m.Msg != 0x0F /*WM_PAINT*/)
base.WndProc(ref m);
else
{
if (m.Msg == 0x0F) // WM_PAINT
base.OnPaint(new PaintEventArgs(Graphics.FromHwnd(Handle), ClientRectangle));
DefWndProc(ref m);
}
}
else base.WndProc(ref m);
}
}
레이블 백 콜러가 투명 할 때 라벨은 처음으로 생성 된 기본 제어의 그림 만 가져옵니다. 레이블 백 콜러가 일정합니다. 그리고 레이블이 자체적으로 페인트 할 때마다 고정 된 색상이나 패턴으로 다시 페인트합니다.
CreateParam을 재정의하면 컨트롤을위한 창이 만드는 방법에 영향을 미치면 실제 투명성이 가능합니다.
WNDPROC를 재정의합니다. 기본 클래스로 전달 해야하는 메시지를 제어합니다. WM_ERASEBKGND 및 WM_PAINT를 여과해야하지만 페인트 이벤트를 트리거해야합니다.
따라서 이전 답변에 대한 의견에 따르면 제어는 기본 동작이며 투명한 것으로 기억 한 것입니다.
어쨌든, USERCONTROL의 배경 속성을 설정했거나 레이블이있는 컨테이너 (패널, 양식, 무엇이든?)에 레이블이 해당 색상을 반영해야합니다 :)
오래된 답변 : WinForms 프로그래밍을 한 지 오래되었지만, 기억대로 라벨은 기본적으로 투명합니까? 따라서 실제 색상을 얻는 유일한 텍스트와 Bacground 색상은 그 뒤에 무엇이든지 모방합니다 :)
달성하고자하는 것을 정확하게 수행 할 수 있습니다. 컨트롤을 가지고 노는 데 약간의 시간이 걸립니다. 투명한 배경으로 레이블 컨트롤을 만들고 진행바 컨트롤 위에 놓을 수 있습니다.
확인하다 내 대답 또 다른 질문입니다.
문제에 대한 설명과 관련하여 Windows는 예상대로 배경 컨트롤에 대한 투명성을 수행하지 않습니다. 회색 배경이 실제로 형태의 표면이라고 생각합니다. 형태 표면과 라벨 사이에 컨트롤이 그려지는 모든 컨트롤은 무시됩니다.
고르다 백콜로, 웹 탭으로 이동하여 투명을 선택하십시오. 다음을 생성합니다.
this.label1.BackColor = System.Drawing.Color.Transparent;