进度条ProgressBar

XAML

<UserControl x:Class="WpfApp1.UC_ProgressBarEx"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             mc:Ignorable="d" 
             d:DesignHeight="200" d:DesignWidth="1000">
    <UserControl.Resources>
        <BooleanToVisibilityConverter x:Key="Boolean2VisibilityConverter"/>
    </UserControl.Resources>
    <Grid>
        <Border Background="White" BorderBrush="Gray"  BorderThickness="1">
            <Border Background="White" BorderThickness="1">
                <Grid>
                    <Grid.Background>
                        <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
                            <GradientStop Color="#FFE5E5E5" Offset="0"/>
                            <GradientStop Color="White" Offset="1"/>
                        </LinearGradientBrush>
                    </Grid.Background>
                    <Grid Width="{Binding ProgressBarWidth, FallbackValue=200, RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}" HorizontalAlignment="Left" MinHeight="6">
                        <Grid.Background>
                            <LinearGradientBrush EndPoint="1,0.5" StartPoint="0,0.5">
                                <GradientStop Color="#FF8BBA91" Offset="0"/>
                                <GradientStop Color="#FF8BBA91" Offset="1"/>
                                <GradientStop Color="#FF9ED76A" Offset="0.8"/>
                                <GradientStop Color="#FF9ED76A" Offset="0.2"/>
                            </LinearGradientBrush>
                        </Grid.Background>
                    </Grid>
                    <Border>
                        <Border.Background>
                            <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
                                <GradientStop Color="#89E2E2E2" Offset="0"/>
                                <GradientStop Color="#C1FFFFFF" Offset="0.5"/>
                                <GradientStop Color="Transparent" Offset="0.52"/>
                            </LinearGradientBrush>
                        </Border.Background>
                    </Border>
                    <TextBlock HorizontalAlignment="Left" VerticalAlignment="Center" x:Name="txtPercent"
                               Text="{Binding Percentage, RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}"
                               Visibility="{Binding PercentageVisible, Converter={StaticResource Boolean2VisibilityConverter}, RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}"
                               />
                </Grid>
            </Border>
        </Border>
    </Grid>
</UserControl>

CS

public partial class UC_ProgressBarEx : UserControl
{
    /// <summary>
    /// 百分比最后是否显示,默认true显示
    /// </summary>
    private readonly bool _bInitVisibility;
    public UC_ProgressBarEx()
    {
        InitializeComponent();
        _bInitVisibility = true;
        ProgressBarWidth = 0;
    }

    /// <summary>
    /// 进度条最小值
    /// </summary>
    public double Minimum
    {
        get { return (double)GetValue(MinimumProperty); }
        set { SetValue(MinimumProperty, value); }
    }
    public static readonly DependencyProperty MinimumProperty = DependencyProperty.Register("Minimum", typeof(double), typeof(UC_ProgressBarEx), new PropertyMetadata(0d, OnMinimumChanged));
    private static void OnMinimumChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        (d as UC_ProgressBarEx).Update();
    }

    /// <summary>
    /// 进度条最大值
    /// </summary>
    public double Maximum
    {
        get { return (double)GetValue(MaximumProperty); }
        set { SetValue(MaximumProperty, value); }
    }
    public static readonly DependencyProperty MaximumProperty = DependencyProperty.Register("Maximum", typeof(double), typeof(UC_ProgressBarEx), new PropertyMetadata(100d, OnMaximumChanged));
    private static void OnMaximumChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        (d as UC_ProgressBarEx).Update();
    }

    /// <summary>
    /// 进度值
    /// </summary>
    public double Value
    {
        get { return (double)GetValue(ValueProperty); }
        set { SetValue(ValueProperty, value); }
    }
    public static readonly DependencyProperty ValueProperty = DependencyProperty.Register("Value", typeof(double), typeof(UC_ProgressBarEx), new PropertyMetadata(0d, OnValueChanged));
    private static void OnValueChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        (d as UC_ProgressBarEx).Update();
    }

    /// <summary>
    /// 百分比是否显示,默认true显示
    /// </summary>
    public bool PercentageVisible
    {
        get { return (bool)GetValue(PercentageVisibleProperty); }
        set { SetValue(PercentageVisibleProperty, value); }
    }
    public static readonly DependencyProperty PercentageVisibleProperty =
        DependencyProperty.Register("PercentageVisible", typeof(bool), typeof(UC_ProgressBarEx), new PropertyMetadata(true));


    /// <summary>
    /// 要显示的数据
    /// </summary>
    public string Percentage
    {
        get { return (string)GetValue(PercentageProperty); }
        private set { SetValue(PercentageProperty, value); }
    }
    public static readonly DependencyProperty PercentageProperty = DependencyProperty.Register("Percentage", typeof(string), typeof(UC_ProgressBarEx), new PropertyMetadata("0%", OnPercentageChanged));
    private static void OnPercentageChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        (d as UC_ProgressBarEx).Update();
    }
    /// <summary>
    /// 进度条宽度
    /// </summary>
    public double ProgressBarWidth
    {
        get { return (double)GetValue(ProgressBarWidthProperty); }
        private set { SetValue(ProgressBarWidthProperty, value); }
    }
    private static readonly DependencyProperty ProgressBarWidthProperty = DependencyProperty.Register("ProgressBarWidth", typeof(double), typeof(UC_ProgressBarEx), null);

    private void Update()
    {
        ProgressBarWidth = Math.Min((Value / (Maximum - Minimum) * this.ActualWidth) - 2, this.ActualWidth - 2);
        txtPercent.Margin = new Thickness(ProgressBarWidth - 50, 0, 0, 0);
        var val = (Value / (Maximum - Minimum) * 100);
        if (val >= 100.00)
        {
            Percentage = "100 %";
            ThreadPool.QueueUserWorkItem(ThreadProc);
        }
        else
        {
            Percentage = val.ToString("0.00") + "%";
        }
    }
    private void ThreadProc(object state)
    {
        Thread.Sleep(1000);
        if (_bInitVisibility)
        {
            this.Dispatcher.Invoke(() =>
            {
                Visibility = Visibility.Visible;
            });
        }
        else
        {
            this.Dispatcher.Invoke(() =>
            {
                Visibility = Visibility.Collapsed;
            });
        }
    }
}

测试

int Sum = 345;
//pbCompleted.PercentageVisible = false;
pbCompleted.Maximum = Sum;
pbCompleted.Value = 0;
lbResult.Text = $"({pbCompleted.Value}/{pbCompleted.Maximum})";
Task.Run(() =>
{
    //for (int i = 0; i < 5; i++)
    //{
    //    this.Dispatcher.Invoke(() =>
    //    {
    //        pbCompleted.Value = 20 * i * pbCompleted.Maximum / 100;
    //    });
    //    Thread.Sleep(300);
    //}
    for (int i = 0; i < Sum; i++)
    {
        this.Dispatcher.Invoke(() =>
        {
            pbCompleted.Value++;
            lbResult.Text = $"({pbCompleted.Value}/{pbCompleted.Maximum})";
        });
        Thread.Sleep(20);
    }
    this.Dispatcher.Invoke(() =>
    {
        btn.IsEnabled = true;
    });
});

posted @ 2019-12-01 15:21  wesson2019  阅读(123)  评论(0)    收藏  举报