wpf 波浪进度条

画了个正弦波图形
这里使用其它方式实现 https://www.bilibili.com/video/BV1GL411H746 ,其它 css 中也看过这个思路

xaml


    <Border
        BorderBrush="#4d4CAF50" BorderThickness="1" ClipToBounds="True" CornerRadius="5">

        <Grid>

            <Grid.RowDefinitions>
                <RowDefinition Height="*" />
                <RowDefinition Height="Auto" />
            </Grid.RowDefinitions>

            <!--  波浪部分  -->
            <Path
                x:Name="WavePath"
                Grid.Row="0"
                Height="5"
                HorizontalAlignment="Stretch" VerticalAlignment="Bottom"
                Fill="#4CAF50">
                <Path.Data>
                    <PathGeometry Figures="M0,5L0,2.319756173196589L13,-3.9940491514794028L26,-1.8181793307025769L39,4.222378001023952L52,1.2879287140357052L65,-4.384117427165996L78,-0.7373666921771697L80,5z" />
                </Path.Data>
            </Path>

            <!--  波浪下半部分为进度条主体, 因为需要与父级高度及进度有关, 所以使用多重绑定,以接收两者变更的事件
            使用转换器将进度转为相应的高度-->
            <Rectangle Grid.Row="1" Fill="#4CAF50">
                <Rectangle.Height>
                    <MultiBinding Converter="{StaticResource ProgressHeightValueConverter}">
                        <Binding Path="Progress" RelativeSource="{RelativeSource AncestorType=UserControl}" />
                        <Binding Path=".ActualHeight" RelativeSource="{RelativeSource AncestorType=UserControl}" />
                    </MultiBinding>
                </Rectangle.Height>
            </Rectangle>

            <!--  显示进度文字描述  -->
            <TextBlock
                Grid.Row="0" Grid.RowSpan="2"
                HorizontalAlignment="Center" VerticalAlignment="Center"
                FontSize="24" Foreground="#4CAF50"
                Text="{Binding RelativeSource={RelativeSource AncestorType=UserControl}, Path=Progress, StringFormat={}{0:#}%, FallbackValue=10.2%}">
                <TextBlock.Effect>
                    <DropShadowEffect
                        BlurRadius="4" Opacity="1" ShadowDepth="0"
                        Color="White" />
                </TextBlock.Effect>
            </TextBlock>

        </Grid>

    </Border>

cs

        // 定时调用,生成波形

        // 取下一步波形的相位差
        var phaseDifference = GetNextPhaseDifference(ref this.currentPhaseDifference);

        // 画出波形
        var figure = CalcWavePathFigure(phaseDifference, wavePath.ActualHeight, wavePath.ActualWidth);

        // 设置波形
        pathGeometry.Figures.Clear();
        pathGeometry.Figures.Add(figure);

    // 计算一次波形
    // height 波形的高度
    // width   要画的波形的长度
    // waveLength 波长
    private static PathFigure CalcWavePathFigure(double phaseDifference, double height, double width, double waveLength = 50)
    {
        var figure = new PathFigure
        {
            IsClosed = true,
            IsFilled = true,
            StartPoint = new Point(0, height), // 起始点
        };

        for (var x = 0; x < width + 5; x += 13)
        {
            // 画一个正弦波
            var y = Math.Sin(1d * x / waveLength * Math.PI * 2 + phaseDifference) * height * 0.9;
            figure.Segments.Add(new LineSegment(new Point(x, y), true));
        }

        // 结束点
        figure.Segments.Add(new LineSegment(new Point(width, height), true));

        return figure;
    }

    // 取下一步波形的相位差
    private static double GetNextPhaseDifference(ref double phaseDifference)
    {
        // 0 - 2PI 之间取值
        /*phaseDifference += 0.1d + Random.Shared.NextDouble() * 0.2d; // 0.2;*/
        phaseDifference += 0.2d;
        if (phaseDifference >= 2 * Math.PI)
        {
            phaseDifference = 0;
        }

        return phaseDifference;
    }
上一篇
下一篇