You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WPF四子棋开发:如何控制动态创建的TextBox控件

WPF动态生成TextBox无法通过名称控制的解决办法

你遇到的问题核心是:WPF动态创建的控件仅设置Name属性不会自动注册到窗口的NameScope中,所以没法直接通过名称定位这些控件。下面给你三种可行的解决方案:

方法一:手动注册NameScope

在窗口构造函数里先初始化NameScope,再给每个动态生成的TextBox注册名称,之后就能通过FindName方法获取控件:

修改后的构造函数代码:

public MainWindow()
{
    InitializeComponent();
    // 初始化窗口的NameScope
    NameScope.SetNameScope(this, new NameScope());

    int x = 100;
    int y = 190;

    for (int i = 1; i < 43; i++)
    {
        TextBox tbx = new TextBox();
        tbx.Name = "Field" + i;
        // 将TextBox注册到NameScope
        NameScope.GetNameScope(this).RegisterName(tbx.Name, tbx);

        tbx.Height = tbx.Width = 50;
        tbx.HorizontalAlignment = HorizontalAlignment.Left;
        tbx.VerticalAlignment = VerticalAlignment.Top;
        tbx.Margin = new Thickness(x, y, 0, 0);
        myGrid.Children.Add(tbx);

        x += 55;
        if (i % 7 == 0)
        {
            y += 55;
            x = 100;
        }
    }
}

按钮点击事件示例(假设按钮名为btnChangeColor):

private void btnChangeColor_Click(object sender, RoutedEventArgs e)
{
    // 修改Field1的背景色为红色
    if (FindName("Field1") is TextBox targetTb)
    {
        targetTb.Background = Brushes.Red;
    }
}

方法二:用集合存储所有游戏格子

在窗口类里定义集合保存所有动态生成的TextBox,后续直接通过集合操作,效率更高:

首先在窗口类中声明集合:

private List<TextBox> _gameFields = new List<TextBox>();

修改构造函数,将每个TextBox添加到集合:

public MainWindow()
{
    InitializeComponent();

    int x = 100;
    int y = 190;

    for (int i = 1; i < 43; i++)
    {
        TextBox tbx = new TextBox();
        tbx.Name = "Field" + i;
        // 添加到集合
        _gameFields.Add(tbx);

        tbx.Height = tbx.Width = 50;
        tbx.HorizontalAlignment = HorizontalAlignment.Left;
        tbx.VerticalAlignment = VerticalAlignment.Top;
        tbx.Margin = new Thickness(x, y, 0, 0);
        myGrid.Children.Add(tbx);

        x += 55;
        if (i % 7 == 0)
        {
            y += 55;
            x = 100;
        }
    }
}

按钮点击事件中操作集合:

private void btnChangeColor_Click(object sender, RoutedEventArgs e)
{
    // 找到Name为Field1的TextBox并修改背景色
    var targetTb = _gameFields.FirstOrDefault(tb => tb.Name == "Field1");
    if (targetTb != null)
    {
        targetTb.Background = Brushes.Blue;
    }

    // 也可以直接通过索引操作(比如修改第3个格子)
    // if (_gameFields.Count > 2)
    // {
    //     _gameFields[2].Background = Brushes.Green;
    // }
}

方法三:遍历容器的子控件查找

不需要额外注册或存储,直接遍历myGrid的Children集合找到目标TextBox:

按钮点击事件代码:

private void btnChangeColor_Click(object sender, RoutedEventArgs e)
{
    foreach (var child in myGrid.Children)
    {
        if (child is TextBox tb && tb.Name == "Field5")
        {
            tb.Background = Brushes.Yellow;
            break;
        }
    }
}

推荐使用方法二,集合操作效率更高,也更适配后续扩展(比如结合MVVM模式绑定数据)。

内容的提问来源于stack exchange,提问作者Luis_Erschig

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.15 08:50:36