从头实现一个WPF条形图

时间如流水,只能流去不流回!

点赞再看,养成习惯,这是您给我创作的动力!

本文 Dotnet9 https://dotnet9.com 已收录,站长乐于分享dotnet相关技术,比如Winform、WPF、ASP.NET Core等,亦有C++桌面相关的Qt Quick和Qt Widgets等,只分享自己熟悉的、自己会的。

阅读导航:

  • 一、先看效果
  • 二、本文背景
  • 三、代码实现
  • 四、文章参考
  • 五、代码下载

一、先看效果

从头实现一个WPF条形图

二、本文背景

有没有这种场景:开源控件库或者收费的控件库,条形图或者柱状图都非常强大,但我的业务就是不符合,就是要自己设计呢?本文通过简单的实现一个条形图功能,以后类似的统计图可以在这上面进行修改,原理是类似的。

三、代码实现

小编使用.Net Core 3.1创建的WPF工程,创建名称为“BarChart”的解决方案后,添加名称为”Bar“的WPF用户控件,这个控件就是上图中的单个柱子,下面是Bar.xaml代码

<UserControl x:Class="BarChart.Bar"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             mc:Ignorable="d" 
             MinHeight="20" Width="Auto" Loaded="UserControl_Loaded">
    <Grid SizeChanged="Grid_SizeChanged">
        <Grid Background="{Binding Background,ElementName=border}" Opacity="0.3"/>
        <Border x:Name="border" Background="{Binding Color}" VerticalAlignment="Bottom" Height="{Binding BarHeight}"/>
        <TextBlock VerticalAlignment="Center" Margin="3" HorizontalAlignment="Center" Text="{Binding Value}" FontSize="20">
            <TextBlock.Effect>
                <DropShadowEffect BlurRadius="1" ShadowDepth="0" Color="White"/>
            </TextBlock.Effect>
        </TextBlock>
    </Grid>
</UserControl>

Bar.xaml.cs代码,主要是绑定前景色及背景色,及柱子百分比值。

using System.ComponentModel;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;

namespace BarChart
{
    /// <summary>
    /// BarChart.xaml 的交互逻辑
    /// </summary>
    public partial class Bar  : UserControl, INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;
        private void NotifyPropertyChanged(string info)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(info));
            }
        }

        private double _value;
        public double Value
        {
            get { return _value; }
            set
            {
                _value = value;
                UpdateBarHeight();
                NotifyPropertyChanged("Value");
            }
        }

        private double maxValue;
        public double MaxValue
        {
            get { return maxValue; }
            set
            {
                maxValue = value;
                UpdateBarHeight();
                NotifyPropertyChanged("MaxValue");
            }
        }

        private double barHeight;
        public double BarHeight
        {
            get { return barHeight; }
            set
            {
                barHeight = value;
                NotifyPropertyChanged("BarHeight");
            }
        }

        private Brush color;
        public Brush Color
        {
            get { return color; }
            set
            {
                color = value;
                NotifyPropertyChanged("Color");
            }
        }

        private void UpdateBarHeight()
        {
            if (maxValue > 0)
            {
                var percent = (_value * 100) / maxValue;
                BarHeight = (percent * this.ActualHeight) / 100;
            }
        }

        public Bar()
        {
            InitializeComponent();

            this.DataContext = this;
            color = Brushes.Black;
        }


        private void UserControl_Loaded(object sender, RoutedEventArgs e)
        {
            UpdateBarHeight();
        }

        private void Grid_SizeChanged(object sender, SizeChangedEventArgs e)
        {
            UpdateBarHeight();
        }
    }
}

主窗体MainWindow.xaml,添加显示的业务数据,目前只是展示了进度值,其他标签只要你看懂了代码,很好加的,比如每根柱子,上面颜色显示一种意义名称、下面显示另一种意义名称。

<Window x:Class="BarChart.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:BarChart"
        mc:Ignorable="d"
        Background="#FF252525" FontFamily="Nontserrrat"
        Title="MainWindow" Height="600" Width="1080" WindowStyle="None" ResizeMode="NoResize" WindowStartupLocation="CenterScreen">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="70"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>

        <Border BorderBrush="Gray" BorderThickness="0 0 0 1">
            <TextBlock Text="Dotnet9.com" VerticalAlignment="Center" Margin="15"
                       Foreground="White" FontSize="24"/>
        </Border>

        <Border Grid.Row="1" Width="500" Height="300" VerticalAlignment="Top"
                HorizontalAlignment="Left" Margin="20" Background="White"
                BorderBrush="Gray" CornerRadius="12">
            <Grid>
                <TextBlock Text="自定义条形图" Margin="10" FontSize="15"/>
                <StackPanel Orientation="Horizontal" Height="200" VerticalAlignment="Bottom">
                    <local:Bar Background="#FF4455AA" Color="#FF88AA55" MaxValue="100" Value="80" Margin="5"/>
                    <local:Bar Background="#FF4335AA" Color="#FF883355" MaxValue="100" Value="26" Margin="5"/>
                    <local:Bar Background="#F26455AA" Color="#FF88A355" MaxValue="100" Value="49" Margin="5"/>
                    <local:Bar Background="#FF4423AA" Color="#FF88A115" MaxValue="100" Value="23" Margin="5"/>
                    <local:Bar Background="#FF4415AA" Color="#FF887955" MaxValue="100" Value="97" Margin="5"/>
                    <local:Bar Background="#FF44513A" Color="#FF896A55" MaxValue="100" Value="68" Margin="5"/>
                </StackPanel>
            </Grid>
        </Border>
    </Grid>
</Window>

四、文章参考

参考:
Design com WPF :    https://www.youtube.com/watch?v=3Rz9YrwrznQ

五、代码下载

文章中代码已经全部贴出,小编这里还是建议:能使用开源的控件库还是使用开源控件库吧,自己定义确实有点麻烦。

本文只是给个例子,方便自定义扩展。

除非注明,文章均由 Dotnet9 整理发布,欢迎转载。

转载请注明:
作者:Dotnet9
链接:https://dotnet9.com/6255.html
来源:Dotnet9
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

发表评论

登录后才能评论