Comment changer la couleur de la barre de progression dans C # .NET 3.5?

J’aimerais faire deux choses sur ma barre de progression.

  1. Changez la couleur verte en rouge.
  2. Retirez les blocs et faites-en une couleur.

Toute information sur ces deux choses que je me demande comment accomplir sera très appréciée!

Merci.

Comme les réponses précédentes ne semblent pas fonctionner avec les styles visuels. Vous devrez probablement créer votre propre classe ou étendre la barre de progression:

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); } } 

EDIT: code mis à jour pour que la barre de progression utilise le style visuel pour l’arrière-plan

OK, il m’a fallu un moment pour lire toutes les réponses et les liens. Voici ce que je suis sorti d’eux:

Exemple de résultats

La réponse acceptée désactive les styles visuels, mais vous permet de définir la couleur selon vos besoins, mais le résultat est clair:

entrer la description de l'image ici

En utilisant la méthode suivante, vous pouvez obtenir quelque chose comme ceci:

entrer la description de l'image ici

Comment

Tout d’abord, incluez ceci si vous ne l’avez pas fait: en using System.Runtime.InteropServices;

Deuxièmement, vous pouvez soit créer cette nouvelle classe, soit placer son code dans une classe non générique existante:

 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); } } 

Maintenant, pour l’utiliser, appelez simplement:

ModifyProgressBarColor.SetState(progressBar1, 2);

Notez le deuxième paramètre dans SetState, 1 = normal (vert); 2 = erreur (rouge); 3 = avertissement (jaune).

J’espère que cela aide!

Ceci est une version sans scintillement du code le plus accepté que vous pouvez trouver comme réponse à cette question. Tout le crédit aux affiches de ces réponses fatales. Merci Dusty, Chris, Matt et Josh!

Comme la demande de “Fueled” dans l’un des commentaires, j’avais aussi besoin d’une version qui se comportait un peu plus … professionnellement. Ce code conserve les styles comme dans le code précédent, mais ajoute un rendu d’image hors écran et une mise en mémoire tampon graphique (et dispose correctement de l’object graphique).

Résultat: tout le bien et pas de scintillement. 🙂

 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(); } } } } 

Dans le concepteur, il vous suffit de définir la propriété ForeColor sur la couleur de votre choix. Dans le cas du rouge, il y a une couleur prédéfinie pour cela.

Pour le faire en code (C #), faites ceci:

 pgs.ForeColor = Color.Red; 

Edit : Oh oui, réglez également le style sur continu. Dans le code, comme ceci:

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

Une autre édition: vous devrez également supprimer la ligne qui lit Application.EnableVisualStyles() de votre Program.cs (ou similaire). Si vous ne pouvez pas faire cela parce que vous voulez que le rest de l’application ait des styles visuels, alors je vous suggère de peindre le contrôle vous-même ou de passer à WPF car ce genre de chose est facile avec WPF. Vous pouvez trouver un tutoriel sur le propriétaire dessinant une barre de progression sur codeplex

Modification à la réponse de dustyburwell. (Je n’ai pas assez de rep pour le modifier moi-même.) Comme sa réponse, cela fonctionne avec les “styles visuels” activés. Vous pouvez simplement définir la propriété ForeColor de la barre de progression dans la vue de conception de la forme.

 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); } } 

En utilisant les réponses de Matt Blaine et Chris Persichetti, j’ai créé une barre de progression qui semble un peu plus jolie tout en permettant un choix de couleurs infini (en gros, j’ai changé une ligne dans la solution de 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); } } } 

Usage:

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

Résultats

Vous pouvez utiliser n'importe quel dégradé que vous aimez!

Télécharger

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

Je viens de mettre cela dans une classe statique.

  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); } 

J’espère que cela aide,

Marc

En règle générale, la barre de progression est thématique ou respecte les préférences de couleur de l’utilisateur. Donc, pour modifier la couleur, vous devez soit désactiver les styles visuels et définir ForeColor soit dessiner le contrôle vous-même.

En ce qui concerne le style continu au lieu des blocs, vous pouvez définir la propriété Style :

 pBar.Style = ProgressBarStyle.Continuous; 

MODIFIER

Au son des choses que vous utilisez le thème XP qui a le prog-bar basé sur le bloc vert. Essayez de basculer votre style d’interface utilisateur vers Windows Classic et testez à nouveau, mais vous devrez peut-être implémenter votre propre événement OnPaint pour qu’il fasse ce que vous voulez dans tous les styles d’interface utilisateur.

Ou, comme quelqu’un d’autre l’a souligné, désactivez les VisualStyles pour votre application.

Original

Autant que je sache, le rendu de la barre de progression se fait en ligne avec le style de thème Windows que vous avez choisi (win2K, xp, vista)

Vous pouvez changer la couleur en définissant la propriété

 ProgressBar.ForeColor 

Je ne suis pas sûr que vous puissiez faire beaucoup plus cependant …

fait du googler

Theres un article de MS KB sur la création d’une barre de progression “Smooth”

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

Je vous suggère de jeter également un oeil à cet article sur CodeProject: Progress-O-Doom . C’est bien!

essayez d’utiliser messsage PBM_SETBARCOLOR, qui devrait faire l’affaire avec SendMessage

Voir http://www.vbforums.com/showthread.php?t=248721 pour un exemple.

Toutes ces méthodes ne fonctionnent pas pour moi, mais cette méthode vous permet de changer la chaîne de couleurs.

Veuillez noter que j’ai trouvé ce code ailleurs sur StackOverflow et que je l’ai légèrement modifié. J’ai depuis oublié où j’ai trouvé ce code et je ne peux pas le lier à cause de cela, désolé pour ça.

Mais de toute façon, j’espère que ce code aide quelqu’un à m’aider.

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

Lorsque le nom “ProgressBar” est utilisé, remplacez-le par votre propre nom de barre de progression. Vous pouvez également déclencher cet événement avec d’autres arguments, mais assurez-vous simplement qu’il est entre crochets.

Changer la Color et la Value (modification instantanée)

Mettre à l’ using System.Runtime.InteropServices; en haut…

Appeler avec ColorBar.SetState(progressBar1, ColorBar.Color.Yellow, myValue);

J’ai remarqué que si vous modifiez la valeur de la barre (quelle est sa taille), elle ne changera pas si la couleur est différente du vert par défaut. J’ai pris le code de user1032613 et ajouté une option Value.

 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 } } 

Juste au cas où quelqu’un chercherait une autre option …. vous pouvez étendre un Panel, l’utiliser comme arrière-plan (blanc ou autre), append un autre Panel à l’intérieur pour le premier plan (la barre mobile). Ensuite, vous avez le contrôle total en changeant la couleur, etc.

Faites simplement un clic droit sur votre projet dans Visual Basic Solution Explorer (où sont vos fichiers vb) et sélectionnez les propriétés dans le menu. Dans la fenêtre qui apparaît, désélectionnez “Activer les styles visuels XP” et maintenant, lorsque vous définissez la couleur, cela devrait fonctionner maintenant.

Oui: Quote: En général, la barre de progression est soit thématique, soit respecte les préférences de couleur de l’utilisateur. Donc, pour modifier la couleur, vous devez soit désactiver les styles visuels et définir ForeColor soit dessiner le contrôle vous-même.

En ce qui concerne le style continu au lieu des blocs, vous pouvez définir la propriété Style :

 pBar.Style = ProgressBarStyle.Continuous; 

ProgressBarStyle.Continuous versus Blocks est inutile avec VistualStyles activé …

Block (s) ne fonctionnera qu’avec les styles visuels désactivés … ce qui rend tout cela incompréhensible (en ce qui concerne la couleur de progression personnalisée).

J’ai utilisé une combinaison de la réponse de William Daniel (avec des styles visuels activés, donc le ForeColor ne sera pas seulement plat sans style) et la réponse de Barry (au texte personnalisé sur la barre de progression) de: Comment mettre du texte sur ProgressBar?

Barre verticale UP For Down en couleur rouge:

 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); } } 

La barre de progression colorée VB.Net qui respecte la réponse WXP Visual Styles est …

J’ai commencé par la réponse de ‘user1032613’ le 17/03/12. Notez que c’est maintenant un module, pas une classe. À partir de là, j’ai converti le code mais il en fallait plus. En particulier, le code converti a montré une fonction DirectCast pour convertir l’entier “state” en un type IntPtr qui ne fonctionnait pas.

 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  _ Private Function SendMessage(hWnd As IntPtr, Msg As UInteger, w As IntPtr, l As IntPtr) As IntPtr End Function  _ 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 

Et encore une fois, appelez ceci dans le code utilisant cette ligne:

 Call ModifyProgressBarColor.SetState(prb, 2) 

BTW – J’ai essayé d’autres couleurs – 0, 4, 5 – elles sont toutes simplement affichées en vert.

Je sais qu’il est trop vieux pour qu’on réponde maintenant … mais quand même, un petit changement à la réponse de @ Daniel pour rectifier le problème de ne pas afficher la barre de progression à valeur zéro. Il suffit de dessiner la progression uniquement si la largeur du rectangle interne est non nulle.

Merci à tous les consortingbuteurs.

  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(); } } } } } 

J’ai trouvé que cela pouvait être fait en dessinant un rectangle à l’intérieur de la barre de progression et en définissant sa largeur en fonction de la valeur actuelle de la progression. J’ai également ajouté un soutien pour le progrès du droit à la gauche. De cette façon, vous n’avez pas besoin d’utiliser l’image, et puisque Rectnalge.Inflate n’est pas appelé, le rectangle dessiné est plus petit.

 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); } } } 

Edit: dans les deux minutes, il m’a fallu lancer vs et vérifier la syntaxe, j’ai été battu avec des réponses bien meilleures. J’aime ce site

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