WPF 自定义一个可以编辑的TextBlock控件,仿照Excel的单元格样式

先看效果

控件代码

[TemplatePart(Name = "Part_DisplayTextBlock", Type = typeof(TextBlock))]
[TemplatePart(Name = "Part_EditTextBox", Type = typeof(TextBox))]
public class EditableTextBlock : Control
{
    // Using a DependencyProperty as the backing store for Text.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty TextProperty =
        DependencyProperty.Register("Text", typeof(string), typeof(EditableTextBlock), new FrameworkPropertyMetadata(default));

    static EditableTextBlock()
    {
        DefaultStyleKeyProperty.OverrideMetadata(typeof(EditableTextBlock), new FrameworkPropertyMetadata(typeof(EditableTextBlock)));
    }

    public string Text
    {
        get { return (string)GetValue(TextProperty); }
        set { SetValue(TextProperty, value); }
    }

    public override void OnApplyTemplate()
    {
        base.OnApplyTemplate();

        var textBlock = GetTemplateChild("Part_DisplayTextBlock") as TextBlock;
        var textBox = GetTemplateChild("Part_EditTextBox") as TextBox;
        if (textBox == null || textBlock == null)
        {
            return;
        }
        //启动的时候设置TextBlock可见,textBox隐藏
        textBlock.Visibility = Visibility.Visible;
        textBox.Visibility = Visibility.Collapsed;
        //给控件的鼠标双击事件挂载一个方法
        MouseDoubleClick += (s, e) =>
        {
            textBlock.Visibility = Visibility.Collapsed;
            textBox.Visibility = Visibility.Visible;
            textBox.Focus();//使TextBox获得焦点
        };
        //给控件的失去焦点事件挂载一个方法
        LostFocus += (s, e) =>
        {
            textBox.Visibility = Visibility.Collapsed;
            textBlock.Visibility = Visibility.Visible;
        };
        给控件的鼠标离开事件挂载一个方法,这个好像不怎么好
        //MouseLeave += (s, e) =>
        //{
        //    textBox.Visibility = Visibility.Collapsed;
        //    textBlock.Visibility = Visibility.Visible;

        //};
    }
}

样式代码

<Style TargetType="{x:Type local:EditableTextBlock}">
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type local:EditableTextBlock}">
                    <Grid Width="{TemplateBinding Width}">
                        <TextBlock
                            x:Name="Part_DisplayTextBlock"
                            HorizontalAlignment="{TemplateBinding HorizontalAlignment}"
                            VerticalAlignment="{TemplateBinding VerticalAlignment}"
                            Text="{TemplateBinding Text}" />
                        <TextBox
                            x:Name="Part_EditTextBox"
                            HorizontalAlignment="{TemplateBinding HorizontalAlignment}"
                            VerticalAlignment="{TemplateBinding VerticalAlignment}"
                            Text="{TemplateBinding Text}" />
                    </Grid>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>

界面

<Window
    x:Class="MvvmToolkit学习.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:local="clr-namespace:MvvmToolkit学习"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    Title="MainWindow"
    Width="800"
    Height="600"
    d:DataContext="{d:DesignInstance Type=local:TestViewModel}"
    mc:Ignorable="d">
    <Window.Resources>
        <Style TargetType="local:EditableTextBlock">
            <Setter Property="VerticalAlignment" Value="Center" />
            <Setter Property="HorizontalAlignment" Value="Center" />
            <Setter Property="Height" Value="50" />
            <Setter Property="Width" Value="200" />
            <Setter Property="FontSize" Value="25" />
        </Style>
    </Window.Resources>
    <Grid>
        <StackPanel HorizontalAlignment="Center" Orientation="Vertical">
            <Grid ShowGridLines="True">
                <Grid.RowDefinitions>
                    <RowDefinition Height="*" />
                    <RowDefinition Height="*" />
                    <RowDefinition Height="*" />
                </Grid.RowDefinitions>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="*" />
                    <ColumnDefinition Width="*" />
                </Grid.ColumnDefinitions>
                <local:EditableTextBlock
                    Grid.Row="0"
                    Grid.Column="0"
                    Text="AAAA" />
                <local:EditableTextBlock
                    Grid.Row="0"
                    Grid.Column="1"
                    Text="AAAA" />
                <local:EditableTextBlock
                    Grid.Row="1"
                    Grid.Column="0"
                    Text="AAAA" />
                <local:EditableTextBlock
                    Grid.Row="1"
                    Grid.Column="1"
                    Text="AAAA" />
                <local:EditableTextBlock
                    Grid.Row="2"
                    Grid.Column="0"
                    Text="AAAA" />
                <local:EditableTextBlock
                    Grid.Row="2"
                    Grid.Column="1"
                    Text="AAAA" />
            </Grid>
            <TextBox Text="BBB" />

        </StackPanel>
    </Grid>
</Window>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值