Una ProgressBar per .NET Gadgeteer (Italiano)

Come accennato in uno post di qualche giorno fa, i controlli grafici forniti da .NET Gadgeteer possono essere facilmente combinati per creare oggetti più complessi. Oggi vediamo come realizzare una ProgressBar, utile per mostrare a video lo stato di avanzamento delle operazioni.

using System;
using Microsoft.SPOT;
using Microsoft.SPOT.Presentation;
using Microsoft.SPOT.Presentation.Controls;
using Microsoft.SPOT.Presentation.Media;

using GT = Gadgeteer;
using Microsoft.SPOT.Presentation.Shapes;

namespace ProgressBarExample
{
    public class ProgressBar : Border
    {
        private Rectangle progressBar;

        private uint minimum;
        public uint Minimum
        {
            get { return minimum; }
            set
            {
                if (value  value)
                    Value = minimum;
            }
        }

        private uint maximum;
        public uint Maximum
        {
            get { return maximum; }
            set
            {
                if (value > minimum)
                    maximum = value;
            }
        }

        private uint step;
        public uint Step {
            get { return step; }
            set { step = value; }
        }

        private uint pbValue;
        public uint Value {
            get { return pbValue; }
            set {
                if (value  maximum)
                    pbValue = maximum;
                else
                    pbValue = value;

                int progressBarWidth = (int)((this.Width * pbValue) / maximum);
                progressBar.Width = progressBarWidth;
            }
        }

        public ProgressBar(int height, int width, GT.Color color)
            : this(height, width, color, color)
        { }

        public ProgressBar(GT.Color color)
            : this(15, 100, color, color)
        { }

        public ProgressBar(int width, GT.Color color)
            : this(15, width, color, color)
        { }

        public ProgressBar(int width, GT.Color startColor, GT.Color endColor)
            : this(15, width, startColor, endColor)
        { }

        public ProgressBar(int height, int width, GT.Color startColor, GT.Color endColor)
        {
            this.BorderBrush = new SolidColorBrush(GT.Color.Black);
            this.SetBorderThickness(2, 2, 2, 2);
            this.Background = new SolidColorBrush(GT.Color.White);
            this.Height = height;
            this.Width = width;

            progressBar = new Rectangle(0, this.Height);
            if (startColor != endColor)
                progressBar.Fill = new LinearGradientBrush(startColor, endColor);
            else
                progressBar.Fill = new SolidColorBrush(startColor);

            progressBar.HorizontalAlignment = HorizontalAlignment.Left;
            this.Child = progressBar;

            minimum = 0;
            maximum = 100;
            step = 5;
        }

        public void PerformStep()
        {
            this.Value += step;
        }
    }
}

Il controllo ProgressBar eredita da Border e vi aggiunge quattro proprietà:

  • Minimum e Maximum rappresentano, rispettivamente, il minimo e il massimo valore che può assumere la barra;
  • Value consente di leggere o impostare il valore attuale della barra di avanzamento;
  • Step indica di quanto viene avanzata la posizione corrente quando viene richiamato il metodo PerformStep.

L’avanzamento della barra è mostrato attraverso un oggetto Rectangle la cui larghezza varia proporzionalmente in base al valore della proprietà Value.  Il riempimento del rettangolo è specificato nel costruttore della ProgressBar e può essere un solo colore, oppure una coppia: in quest’ultimo caso, il colore della barra sarà sfumato dal primo al secondo colore.

Vediamo come utilizzare tale controllo con un esempio che sfrutta i moduli Button e Display di GHI Electronics. Nella routine SetupWindow definiamo la ProgressBar e la aggiungiamo all’interfaccia:

private ProgressBar progressBar;
private Text txtProgressBarValue;

private void SetupWindow()
{
    Window window = display.WPFWindow;
    Font baseFont = Resources.GetFont(Resources.FontResources.NinaB);

    Canvas canvas = new Canvas();
    window.Child = canvas;

    Text txtInstruction = new Text(baseFont, "Push the button to increment bar value.");
    canvas.Children.Add(txtInstruction);
    Canvas.SetTop(txtInstruction, 80);
    Canvas.SetLeft(txtInstruction, 30);

    progressBar = new ProgressBar(200, GT.Color.FromRGB(0, 128, 0));
    progressBar.Minimum = 0;
    progressBar.Maximum = 100;

    canvas.Children.Add(progressBar);
    Canvas.SetTop(progressBar, 120);
    Canvas.SetLeft(progressBar, 50);

    txtProgressBarValue = new Text(baseFont, "Current value: 0");
    canvas.Children.Add(txtProgressBarValue);
    Canvas.SetTop(txtProgressBarValue, 140);
    Canvas.SetLeft(txtProgressBarValue, 90);
}

In questo caso, la barra ha una larghezza di 200 pixel e il colore di riempimento è una tonalità di verde (RGB(0, 128, 0)). Vogliamo fare in modo che, premendo il bottone, il valore della barra venga incrementato di 5 e l’oggetto txtProgressBarValue mostri il valore corrente. Nella routine dell’evento ButtonPressed dobbiamo quindi scrivere:

private void button_ButtonPressed(Button sender, Button.ButtonState state)
{
    progressBar.Value = progressBar.Value + 5;
    txtProgressBarValue.TextContent = "Current value: " + progressBar.Value.ToString();
}

In conclusione, il file Program.cs completo della nostra applicazione è il seguente:

using System;
using Microsoft.SPOT;
using Microsoft.SPOT.Presentation;
using Microsoft.SPOT.Presentation.Controls;
using Microsoft.SPOT.Presentation.Media;

using GT = Gadgeteer;
using GTM = Gadgeteer.Modules;
using Gadgeteer.Modules.GHIElectronics;

namespace ProgressBarExample
{
    public partial class Program
    {
        void ProgramStarted()
        {
            button.ButtonPressed += new Button.ButtonEventHandler(button_ButtonPressed);

            SetupWindow();
            Debug.Print("Program Started");
        }

        private ProgressBar progressBar;
        private Text txtProgressBarValue;

        private void SetupWindow()
        {
            Window window = display.WPFWindow;
            Font baseFont = Resources.GetFont(Resources.FontResources.NinaB);

            Canvas canvas = new Canvas();
            window.Child = canvas;

            Text txtInstruction = new Text(baseFont, "Push the button to increment bar value.");
            canvas.Children.Add(txtInstruction);
            Canvas.SetTop(txtInstruction, 80);
            Canvas.SetLeft(txtInstruction, 30);

            progressBar = new ProgressBar(200, GT.Color.FromRGB(0, 128, 0));
            progressBar.Minimum = 0;
            progressBar.Maximum = 100;
            progressBar.Step = 5;

            canvas.Children.Add(progressBar);
            Canvas.SetTop(progressBar, 120);
            Canvas.SetLeft(progressBar, 50);

            txtProgressBarValue = new Text(baseFont, "Current value: 0");
            canvas.Children.Add(txtProgressBarValue);
            Canvas.SetTop(txtProgressBarValue, 140);
            Canvas.SetLeft(txtProgressBarValue, 90);
        }

        private void button_ButtonPressed(Button sender, Button.ButtonState state)
        {
            progressBar.Value = progressBar.Value + 5;
            txtProgressBarValue.TextContent = "Current value: " + progressBar.Value.ToString();
        }
    }
}

L’applicazione di esempio è disponibile per il download.

ProgressBarExample.zip

Advertisements

,

  1. #1 by Chida on November 29, 2011 - 6:03 AM

    molto utile sarebbe anche un video per vedere già il risultato.

    Ottime informazioni

    • #2 by Marco Minerva on November 29, 2011 - 6:25 AM

      Hai ragione, ci stavo pensando già da un po’… Devo attrezzarmi per mettere su qualche piccolo video.

  2. #3 by Michael Dodaro on November 29, 2011 - 8:01 AM

    • #4 by Marco Minerva on November 29, 2011 - 8:29 AM

      Thank you very much Michael, I have updated the post with your video!

  3. #5 by Michael Dodaro on November 29, 2011 - 11:08 AM

    No problem, Marco. I’m happy to have your fine posts on the blog. I’ll also translate this one to English as soon as I get a spare moment.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: