实现一个CustomDrawnElement类

CustomDrawnElement.cs

using Avalonia;
using Avalonia.Controls;
using Avalonia.Input;
using Avalonia.Media;

namespace Shares.Avalonia.CustomControls
{
    public class CustomDrawnElement : Control
    {
        // BackgroundColor property
        public static readonly StyledProperty<Color> BackgroundColorProperty =
            AvaloniaProperty.Register<CustomDrawnElement, Color>(nameof(BackgroundColor), Colors.Yellow);

        public Color BackgroundColor
        {
            get => GetValue(BackgroundColorProperty);
            set => SetValue(BackgroundColorProperty, value);
        }

        // Mouse position storage (no underscore)
        private Point? mousePosition;

        public CustomDrawnElement()
        {
            // Enable mouse events
            PointerMoved += OnPointerMoved;
            PointerExited += OnPointerExited;
        }

        // Update mouse position when pointer moves
        private void OnPointerMoved(object? sender, PointerEventArgs e)
        {
            mousePosition = e.GetPosition(this);
            InvalidateVisual();
        }

        // Reset when pointer leaves
        private void OnPointerExited(object? sender, PointerEventArgs e)
        {
            mousePosition = null;
            InvalidateVisual();
        }

        // Create the brush based on hover state
        private IBrush GetForegroundBrush()
        {
            // If pointer not over → solid brush
            if (mousePosition == null)
                return new SolidColorBrush(BackgroundColor);

            // Calculate relative origin
            var pos = mousePosition.Value;

            double relativeX = Bounds.Width > 0 ? pos.X / Bounds.Width : 0.5;
            double relativeY = Bounds.Height > 0 ? pos.Y / Bounds.Height : 0.5;

            return new RadialGradientBrush
            {
                GradientOrigin = new RelativePoint(relativeX, relativeY, RelativeUnit.Relative),
                Center = new RelativePoint(relativeX, relativeY, RelativeUnit.Relative),
                RadiusX = new RelativeScalar(0.8, RelativeUnit.Relative),
                RadiusY = new RelativeScalar(0.8, RelativeUnit.Relative),
                GradientStops =
                {
                    new GradientStop(Colors.White, 0),
                    new GradientStop(BackgroundColor, 1)
                }
            };
        }

        // Draw the element
        public override void Render(DrawingContext context)
        {
            base.Render(context);

            var rect = new Rect(Bounds.Size);
            context.FillRectangle(GetForegroundBrush(), rect);
        }
    }
}

CustomDrawnElementTest.axaml代码

<Window xmlns="https://github.com/avaloniaui"
        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"
        Height="300" Width="300"
        x:Class="AvaloniaUI.CustomDrawnElementTest"
        Title="CustomDrawnElementTest">
    <Grid Margin="5" RowDefinitions="*,auto">
        <CustomDrawnElement BackgroundColor="{Binding #lstColors.SelectedItem}"/>
        <StackPanel Grid.Row="1" Orientation="Horizontal" Margin="5">
            <TextBlock VerticalAlignment="Center">Background Color:  </TextBlock>
            <ComboBox Name="lstColors" Width="100" SelectedIndex="0">
                <Color>#FFFF00</Color>
                <Color>#0000FF</Color>
                <Color>#00FF00</Color>
            </ComboBox>
        </StackPanel>
    </Grid>
</Window>

CustomDrawnElementTest.axaml.cs代码

using Avalonia;
using Avalonia.Controls;
using Avalonia.Markup.Xaml;

namespace AvaloniaUI;

public partial class CustomDrawnElementTest : Window
{
    public CustomDrawnElementTest()
    {
        InitializeComponent();
    }
}

运行效果

image

 

posted on 2025-11-30 08:05  dalgleish  阅读(0)  评论(0)    收藏  举报