IT

C # .NET 3.5에서 진행률 표시 줄의 색상을 변경하는 방법은 무엇입니까?

lottoking 2020. 9. 17. 08:10
반응형

C # .NET 3.5에서 진행률 표시 줄의 색상을 변경하는 방법은 무엇입니까?


진행률 표시 줄에서 두 가지 작업을하고 싶습니다.

  1. 녹색을 빨간색으로 변경하십시오.
  2. 블록을 제거하고 단색으로 만듭니다.

이 두 가지를 달성하는 방법에 대한 정보는 대단히 감사 할 것입니다!

감사합니다.


이전 시청은 비주얼 스타일에서 작동하지 않는 시청. 자신만의 클래스를 만들거나 진행률 표시 줄을 확장해야 할 것입니다.

public class NewProgressBar : ProgressBar
{
    public NewProgressBar()
    {
        this.SetStyle(ControlStyles.UserPaint, true);
    }

    protected override void OnPaint(PaintEventArgs e)
    {
        Rectangle rec = e.ClipRectangle;

        rec.Width = (int)(rec.Width * ((double)Value / Maximum)) - 4;
        if(ProgressBarRenderer.IsSupported)
           ProgressBarRenderer.DrawHorizontalBar(e.Graphics, e.ClipRectangle);
        rec.Height = rec.Height - 4;
        e.Graphics.FillRectangle(Brushes.Red, 2, 2, rec.Width, rec.Height);
    }
}

편집 : 진행률 표시 줄이 배경에 비주얼 스타일을 사용하도록 코드를 업데이트했습니다.


좋아, 모든 답변과 링크를 읽는 데 시간이 걸렸습니다. 내가 얻은 것은 다음과 같다.

샘플 결과

허용되는 옵션은 활주합니다.

여기에 이미지 설명 입력

다음 방법을 사용하면 대신 다음과 같은 것을 얻을 수 있습니다.

여기에 이미지 설명 입력

어떻게

먼저 다음을 수행하지 않은 경우를 포함합니다. using System.Runtime.InteropServices;

둘째,이 새 클래스를 만들거나 기존의 static비 제네릭 클래스 에 해당 코드를 넣을 수 있습니다 .

public static class ModifyProgressBarColor
{
    [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = false)]
    static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, IntPtr w, IntPtr l);
    public static void SetState(this ProgressBar pBar, int state)
    {
        SendMessage(pBar.Handle, 1040, (IntPtr)state, IntPtr.Zero);
    }
}

이제 사용하신 다음을 호출하십시오.

ModifyProgressBarColor.SetState(progressBar1, 2);

SetState의 두 번째 응답 변수는 1 = 정상 (녹색)입니다. 2 = 오류 (빨간색); 3 = 경고 (노란색).

도움이 되셨기를 바랍니다.


이 질문에 대한 답으로 수있는 가장 많이 사용되는 코드의 깜박임없는 버전입니다. 그 치명적인 답변의 포스터에 대한 모든 신용. Dusty, Chris, Matt, Josh에게 감사드립니다!

게임 중 하나에서 "Fueled"의 요청처럼, 나는 또한 좀 더 전문적인 버전이 필요했습니다. 이 코드는 이전 코드에서와 같이 스타일을 유지하지만 오프 스크린 이미지 언어 및 그래픽 버퍼링을 추가로 처리합니다.

결과 : 모든 것이 예방임이 없습니다. :)

public class NewProgressBar : ProgressBar
{
    public NewProgressBar()
    {
        this.SetStyle(ControlStyles.UserPaint, true);
    }

    protected override void OnPaintBackground(PaintEventArgs pevent)
    {
        // None... Helps control the flicker.
    }

    protected override void OnPaint(PaintEventArgs e)
    {
        const int inset = 2; // A single inset value to control teh sizing of the inner rect.

        using (Image offscreenImage = new Bitmap(this.Width, this.Height))
        {
            using (Graphics offscreen = Graphics.FromImage(offscreenImage))
            {
                Rectangle rect = new Rectangle(0, 0, this.Width, this.Height);

                if (ProgressBarRenderer.IsSupported)
                    ProgressBarRenderer.DrawHorizontalBar(offscreen, rect);

                rect.Inflate(new Size(-inset, -inset)); // Deflate inner rect.
                rect.Width = (int)(rect.Width * ((double)this.Value / this.Maximum));
                if (rect.Width == 0) rect.Width = 1; // Can't draw rec with width of 0.

                LinearGradientBrush brush = new LinearGradientBrush(rect, this.BackColor, this.ForeColor, LinearGradientMode.Vertical);
                offscreen.FillRectangle(brush, inset, inset, rect.Width, rect.Height);

                e.Graphics.DrawImage(offscreenImage, 0, 0);
                offscreenImage.Dispose();
            }
        }
    }
}

디자이너에서는 ForeColor 속성을 원하는 색상으로 설정하기 만하면됩니다. Red의 경우 미리 정의 된 색상이 있습니다.

코드 (C #)에서 수행 한 다음 수행하십시오.

pgs.ForeColor = Color.Red;

편집 : 예, 스타일도 연속으로 설정하십시오. 코드에서 다음과 가변합니다.

pgs.Style = System.Windows.Forms.ProgressBarStyle.Continuous;

또 다른 편집 : 또한 Application.EnableVisualStyles()자신의 Program.cs(또는 유사한) 에서 읽는 줄을 제거해야 우리합니다 . 나머지 응용 프로그램이 있기 때문에 작업을 수행 할 수 있으므로 WPF에서는 작업을 수행 할 수 있습니다. 쉽기 때문에 컨트롤을 직접 페인팅하거나 WPF로 이동하는 것이 좋습니다. Codeplex 에서 진행률 표시 줄 그리는 소유자에 대한 안내를 사용할 수 있습니다.


Matt Blaine과 Chris Persichetti의 답변을 사용하여 무한한 색상 선택을 허용하면서 조금 더 멋지게 보이는 진행률 줄을 만들었습니다 (기본적으로 Matt의 솔루션에서 한 줄을 변경했습니다).

ProgressBarEx :

using System;
using System.Windows.Forms;
using System.Drawing;
using System.Drawing.Drawing2D;

namespace QuantumConcepts.Common.Forms.UI.Controls
{
    public class ProgressBarEx : ProgressBar
    {
        public ProgressBarEx()
        {
            this.SetStyle(ControlStyles.UserPaint, true);
        }

        protected override void OnPaint(PaintEventArgs e)
        {
            LinearGradientBrush brush = null;
            Rectangle rec = new Rectangle(0, 0, this.Width, this.Height);
            double scaleFactor = (((double)Value - (double)Minimum) / ((double)Maximum - (double)Minimum));

            if (ProgressBarRenderer.IsSupported)
                ProgressBarRenderer.DrawHorizontalBar(e.Graphics, rec);

            rec.Width = (int)((rec.Width * scaleFactor) - 4);
            rec.Height -= 4;
            brush = new LinearGradientBrush(rec, this.ForeColor, this.BackColor, LinearGradientMode.Vertical);
            e.Graphics.FillRectangle(brush, 2, 2, rec.Width, rec.Height);
        }
    }
}

용법 :

progressBar.ForeColor = Color.FromArgb(255, 0, 0);
progressBar.BackColor = Color.FromArgb(150, 0, 0);

결과

원하는 전세계를 사용할 수 있습니다!

다운로드

https://skydrive.live.com/?cid=0EDE5D21BDC5F270&id=EDE5D21BDC5F270%21160&sc=documents#


dustyburwell의 대답에 대한 수정. (저는 그것을 직접 편집 할 충분한 담당자가 없습니다.) 그의 대답과 대답 "비주얼 스타일"이 활성화 된 상태에서 작동합니다. 어떤 폼의 디자인보기에서 진행률 표시 줄의 ForeColor 속성을 수 있습니다.

using System;
using System.Windows.Forms;
using System.Drawing;

public class ProgressBarEx : ProgressBar
{
    private SolidBrush brush = null;

    public ProgressBarEx()
    {
        this.SetStyle(ControlStyles.UserPaint, true);
    }

    protected override void OnPaint(PaintEventArgs e)
    {
        if (brush == null || brush.Color != this.ForeColor)
            brush = new SolidBrush(this.ForeColor);

        Rectangle rec = new Rectangle(0, 0, this.Width, this.Height);
        if (ProgressBarRenderer.IsSupported)
            ProgressBarRenderer.DrawHorizontalBar(e.Graphics, rec);
        rec.Width = (int)(rec.Width * ((double)Value / Maximum)) - 4;
        rec.Height = rec.Height - 4;
        e.Graphics.FillRectangle(brush, 2, 2, rec.Width, rec.Height);
    }
}

나는 정적 정적 클래스에 넣었습니다.

  const int WM_USER = 0x400;
  const int PBM_SETSTATE = WM_USER + 16;
  const int PBM_GETSTATE = WM_USER + 17;

  [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = false)]
  static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);

  public enum ProgressBarStateEnum : int
  {
   Normal = 1,
   Error = 2,
   Paused = 3,
  }

  public static ProgressBarStateEnum GetState(this ProgressBar pBar)
  {
   return (ProgressBarStateEnum)(int)SendMessage(pBar.Handle, PBM_GETSTATE, IntPtr.Zero, IntPtr.Zero);
  }

  public static void SetState(this ProgressBar pBar, ProgressBarStateEnum state)
  {
   SendMessage(pBar.Handle, PBM_SETSTATE, (IntPtr)state, IntPtr.Zero);
  } 

도움이 되셨기를 바랍니다.

마크


일반적으로 진행률 줄은 테마가 또는 사용자의 표시 색상 기본 설정을 준비합니다. 따라서 색상을 변경 비용 스타일을 끄고 ForeColor컨트롤을 직접 설정 하거나 그려야합니다.

블록 대신 연속 스타일의 경우 Style속성을 수 있습니다 .

pBar.Style = ProgressBarStyle.Continuous;

편집하다

녹색 블록 기반 프로그램 막대가있는 XP 테마를 사용하는 소리로. UI 스타일을 Windows 클래식으로 전환하고 다시 테스트합니다.하지만 모든 UI 스타일에서 원하는 작업을 수행 할 고유 한 OnPaint 이벤트를 구현해야합니다.

또는 다른 사람이 지적했듯이 애플리케이션의 VisualStyles를 중지하십시오.

실물

내가 아는 한 진행률 표시 줄의 인라인 선택한 Windows 테마 스타일 (win2K, xp, vista)과 함께 발생합니다.

속성을 설정하여 색상을 설명 수 있습니다.

ProgressBar.ForeColor

하지만 더 많은 것을 할 수 있을지 모르겠습니다 ...

인터넷 검색을 좀 해

MS KB에서 "부드러운"진행률 표시 줄 만들기에 대한 기사가 있습니다.

http://support.microsoft.com/kb/323116


메시지 PBM_SETBARCOLOR를 사용합니다. SendMessage로 트릭을 수행해야합니다.

예제는 http://www.vbforums.com/showthread.php?t=248721참조 하십시오 .


이 모든 방법이 저것 작동하지 않지만 그러나이 방법을 사용하면 색상이 있습니다.

이 코드는 StackOverflow의 다른 곳에서 발견하여 약간 변경했습니다. 나는이 코드를 어디에서 찾았는지 유감스럽게도 확실한 수 없습니다.

그러나 어쨌든 나는이 코드가 나를 도왔던 누군가에게 도움이되기를 바랍니다.

private void ProgressBar_MouseDown(object sender, MouseButtonEventArgs e)
    {
        var converter = new System.Windows.Media.BrushConverter();
        var brush = (Brush)converter.ConvertFromString("#FFB6D301");
        ProgressBar.Foreground = brush;
    }

"ProgressBar"라는 이름이 사용되는 곳에서 자신의 진행률 표시 줄 이름으로 바꿉니다. 다른 인수 로이 이벤트를 트리거 할 수도 있습니다. 내부 괄호가 어딘가에 있는지 확인하십시오.


변경 ColorValue(즉시 변경)

넣어 using System.Runtime.InteropServices;상단에 ...

전화 ColorBar.SetState(progressBar1, ColorBar.Color.Yellow, myValue);

막대의 값 (크기)을 변경하면 기본 녹색이 아닌 다른 색상이면 변경되지 않는 것이 거의 없습니다. user1032613의 코드를 가져 와서 값 옵션을 추가했습니다.

public static class ColorBar
{
    [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = false)]
    static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, IntPtr w, IntPtr l);
    public enum Color { None, Green, Red, Yellow }

    public static void SetState(this ProgressBar pBar, Color newColor, int newValue)
    {
        if (pBar.Value == pBar.Minimum)  // If it has not been painted yet, paint the whole thing using defualt color...
        {                                // Max move is instant and this keeps the initial move from going out slowly 
            pBar.Value = pBar.Maximum;   // in wrong color on first painting
            SendMessage(pBar.Handle, 1040, (IntPtr)(int)Color.Green, IntPtr.Zero);
        }
        pBar.Value = newValue;
        SendMessage(pBar.Handle, 1040, (IntPtr)(int)Color.Green, IntPtr.Zero);     // run it out to the correct spot in default
        SendMessage(pBar.Handle, 1040, (IntPtr)(int)newColor, IntPtr.Zero);        // now turn it the correct color
    }

}

다른 옵션을 찾는 경우를 대비하여 패널을 확장하고, 배경 (흰색 또는 기타)으로 사용하고, 전경 (이동 막대)을 위해 내부에 패널 패널을 추가 할 수 있습니다. 그런 다음 색상 등을 완전히 제어 할 수 있습니다.


Visual Basic 솔루션 탐색기 (vb 파일이있는 위치)에서 프로젝트를 마우스 오른쪽 단추로 클릭하고 메뉴에서 선택하기 만하면됩니다. 팝업 창에서 "XP 비주얼 스타일 활성화"를 선택 해제하면 이제 전면 색상을 사용할 때 작동합니다.


Јοеу : 인용구 : 일반적으로 진행률 표시 줄은 테마가 있거나 사용자의 색상 기본 설정을 사용합니다. 따라서 색상을 변경 비용 스타일을 끄고 ForeColor컨트롤을 직접 설정 하거나 그려야합니다.

블록 대신 연속 스타일의 경우 Style속성을 수 있습니다 .

pBar.Style = ProgressBarStyle.Continuous;

ProgressBarStyle.Continuous 대 Blocks는 VistualStyles를 활성화하면 쓸모가 없습니다 ...

블록 (들)은 비주얼 스타일이 모든 상태에서 작동합니다 ...이 사용자 정의 진행률 논점으로 작동합니다 ...이 사용자 정의 진행률 색상과 관련하여 vistual 스타일이있는 경우 앞색을 기준으로 표시됩니다. 색상을 지정해야합니다.

William Daniel의 대답 (비주얼 스타일이 활성화되어 있으므로 ForeColor가 스타일없이 평평하지 않을 것임)과 Barry의 대답 (진행률 표시 줄의 사용자 지정 텍스트에)의 조합을 사용했습니다. ProgressBar에 텍스트를 넣는 방법은 무엇입니까?


빨간색으로 아래로 수직 막대 :

using System;
using System.Windows.Forms;
using System.Drawing;



public class VerticalProgressBar : ProgressBar
{


    protected override CreateParams CreateParams
    {
        get
        {
            CreateParams cp = base.CreateParams;
            cp.Style |= 0x04;
            return cp;

        }
    }
    private SolidBrush brush = null;

    public VerticalProgressBar()
    {
        this.SetStyle(ControlStyles.UserPaint, true);
    }

    protected override void OnPaint(PaintEventArgs e)
    {
        if (brush == null || brush.Color != this.ForeColor)
            brush = new SolidBrush(this.ForeColor);

        Rectangle rec = new Rectangle(0, 0, this.Width, this.Height);
        if (ProgressBarRenderer.IsSupported)
        ProgressBarRenderer.DrawVerticalBar(e.Graphics, rec);
        rec.Height = (int)(rec.Height * ((double)Value / Maximum)) - 4;
        rec.Width = rec.Width - 4;
        e.Graphics.FillRectangle(brush, 2, 2, rec.Width, rec.Height);

    } 
}

WXP Visual Styles 답변을 존중하는 VB.Net 컬러 진행률 표시 줄은 ...

나는 12/3/17에 'user1032613'의 답변으로 시작했습니다. 이것은 이제 클래스가 아니라 모듈입니다. 거기에서 나는 코드를 변환했지만 더 많은 것이 필요했습니다. 특히 변환 된 코드는 '상태'정수를 작동하지 않는 IntPtr 유형으로 변환하는 DirectCast 함수를 보여줍니다.

Imports System.Runtime.InteropServices

Public Module ModifyProgressBarColor

    Private Declare Function SendMessage Lib "User32" Alias "SendMessageA" (ByVal hWnd As Long, ByVal wMsg As Long, ByVal wParam As Long, lParam As Long) As Long

    <DllImport("user32.dll", CharSet:=CharSet.Auto, SetLastError:=False)> _
    Private Function SendMessage(hWnd As IntPtr, Msg As UInteger, w As IntPtr, l As IntPtr) As IntPtr
    End Function

    <System.Runtime.CompilerServices.Extension()> _
    Public Sub SetState(pBar As ProgressBar, state As Integer)

        '-- Convert state as integer to type IntPtr
        Dim s As IntPtr
        Dim y As Integer = state
        s = IntPtr.op_Explicit(y)

        '-- Modify bar color
        SendMessage(pBar.Handle, 1040, s, IntPtr.Zero)

    End Sub

End Module

그리고 다시 다음 줄을 사용하여 코드를 호출하십시오.

Call ModifyProgressBarColor.SetState(prb, 2)

BTW- 다른 색상을 시도했습니다 -0, 4, 5- 모두 녹색으로 표시되었습니다.


나는 지금 대답하기에는 너무 오래 예방법은 알고 있습니다. 그러나 여전히 0 값 진행률 막대를 표시하지 않는 문제를 해결 하기 위해 @ Daniel 의 대답을 약간 조정했습니다 . 내부 사각형의 너비가 0이 아닌 경우에만 진행률을 그립니다.

모든 기여자에게 감사드립니다.

        public class ProgressBarEx : ProgressBar
        {
            public ProgressBarEx()
            {
                this.SetStyle(ControlStyles.UserPaint, true);
            }

            protected override void OnPaintBackground(PaintEventArgs pevent){}
                // None... Helps control the flicker.                

            protected override void OnPaint(PaintEventArgs e)
            {
                const int inset = 2; // A single inset value to control teh sizing of the inner rect.

                using (Image offscreenImage = new Bitmap(this.Width, this.Height))
                {
                    using (Graphics offscreen = Graphics.FromImage(offscreenImage))
                    {
                        Rectangle rect = new Rectangle(0, 0, this.Width, this.Height);

                        if (ProgressBarRenderer.IsSupported)
                            ProgressBarRenderer.DrawHorizontalBar(offscreen, rect);

                        rect.Inflate(new Size(-inset, -inset)); // Deflate inner rect.
                        rect.Width = (int)(rect.Width * ((double)this.Value / this.Maximum));

                        if (rect.Width != 0)
                        {
                            LinearGradientBrush brush = new LinearGradientBrush(rect, this.ForeColor, this.BackColor, LinearGradientMode.Vertical);
                            offscreen.FillRectangle(brush, inset, inset, rect.Width, rect.Height);
                            e.Graphics.DrawImage(offscreenImage, 0, 0);
                            offscreenImage.Dispose();
                        }
                    }
                }
            }
        }

진행률 표시 줄 안에 사각형을 그리고 진행률의 현재 값에 따라 너비를 설정하면됩니다. 나는 또한 오른쪽에서 계속 진행하는 것에 대한 지원을 추가했습니다. 이렇게하면 이미지를 사용할 필요가 없습니다. Rectnalge.Inflate가 호출되지 않기 때문에 사각형이 더 작습니다.

public partial class CFProgressBar : ProgressBar
{
    public CFProgressBar()
    {
        InitializeComponent();
        this.SetStyle(ControlStyles.UserPaint, true);
    }

    protected override void OnPaintBackground(PaintEventArgs pevent) { }

    protected override void OnPaint(PaintEventArgs e)
    {
        double scaleFactor = (((double)Value - (double)Minimum) / ((double)Maximum - (double)Minimum));
        int currentWidth = (int)((double)Width * scaleFactor);
        Rectangle rect;
        if (this.RightToLeftLayout)
        {
            int currentX = Width - currentWidth;
            rect = new Rectangle(currentX, 0, this.Width, this.Height);
        }
        else
            rect = new Rectangle(0, 0, currentWidth, this.Height);

        if (rect.Width != 0)
        {
            SolidBrush sBrush = new SolidBrush(ForeColor);
            e.Graphics.FillRectangle(sBrush, rect);
        }
    }
}

가장 간단한 방법은 빠른 수정일 뿐이지 만 Program.cs에서 Application.EnableVisualStyles ()를 삭제하거나 주석 처리하거나 Main 함수를 포함하는 부분의 이름을 포함합니다. 그 후에 progressBar.ForeColor = Color.TheColorYouDesire;

static void Main()
        {
            //Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new Form1());
         }

편집 : 두 분에서 내가 대를 발사하고 훨씬 더 나은 응답으로 구타당한 구문을 확인하는 데 걸렸습니다. 나는이 사이트를 좋아한다.

        progressBar1 = new ProgressBar();
        progressBar1.ForeColor = Color.Red;

참고 URL : https://stackoverflow.com/questions/778678/how-to-change-the-color-of-progressbar-in-c-sharp-net-3-5

반응형