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

WPF棋盘游戏开发:如何在10×10棋盘上放置初始4个棋子

WPF棋盘游戏:控制初始棋子显示与自定义棋子样式的解决办法

1. 拆分组件职责,避免棋子与棋盘格子绑定死

你之前的问题核心是GamePiece.xaml同时负责棋盘格子和棋子生成,导致每个格子都带棋子,没法控制数量。建议把两者拆分:

  • GamePiece.xaml只做棋盘格子的样式(比如背景色、边框),不处理棋子逻辑;
  • 新建PlayerPiece.xaml(或直接在视图里写模板)专门负责棋子的显示(圆形/图片)。

2. ViewModel层维护棋子集合

在PlayerViewModel里单独维护一个只包含初始棋子的可观察集合,每个棋子记录坐标和样式信息:

public class ChessPiece : INotifyPropertyChanged
{
    private int _x;
    private int _y;
    // 用图片路径或画笔区分样式,按需选择
    private string _pieceImage;
    private Brush _pieceColor;

    public int X
    {
        get => _x;
        set { _x = value; OnPropertyChanged(); }
    }

    public int Y
    {
        get => _y;
        set { _y = value; OnPropertyChanged(); }
    }

    public string PieceImage
    {
        get => _pieceImage;
        set { _pieceImage = value; OnPropertyChanged(); }
    }

    public Brush PieceColor
    {
        get => _pieceColor;
        set { _pieceColor = value; OnPropertyChanged(); }
    }

    public event PropertyChangedEventHandler PropertyChanged;
    protected void OnPropertyChanged([CallerMemberName] string prop = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(prop));
    }
}

// 在PlayerViewModel中初始化棋子
public ObservableCollection<ChessPiece> PlayerPieces { get; } = new();

public PlayerViewModel()
{
    // 按你的初始规则添加4个棋子,坐标自定义
    PlayerPieces.Add(new ChessPiece { X = 0, Y = 0, PieceColor = Brushes.DodgerBlue });
    PlayerPieces.Add(new ChessPiece { X = 0, Y = 1, PieceColor = Brushes.DodgerBlue });
    PlayerPieces.Add(new ChessPiece { X = 1, Y = 0, PieceColor = Brushes.DodgerBlue });
    PlayerPieces.Add(new ChessPiece { X = 1, Y = 1, PieceColor = Brushes.DodgerBlue });
}

3. View层分层布局,独立渲染棋盘与棋子

在GameView.xaml里用Grid嵌套两个ItemsControl:底层渲染棋盘格子,上层渲染棋子(用Canvas定位到对应坐标)。假设每个格子大小是50x50:

<Grid>
    <!-- 棋盘格子 -->
    <ItemsControl ItemsSource="{Binding BoardCells}">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <UniformGrid Rows="10" Columns="10" />
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <local:GamePiece Width="50" Height="50" />
            </DataTemplate>
        </ItemsControl.ItemTemplate>
    </ItemsControl>

    <!-- 玩家棋子 -->
    <ItemsControl ItemsSource="{Binding PlayerPieces}">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <Canvas />
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <!-- 圆形棋子示例 -->
                <Ellipse Width="40" Height="40" Fill="{Binding PieceColor}"
                         Canvas.Left="{Binding X, Converter={StaticResource CoordToPixel}, ConverterParameter=50}"
                         Canvas.Top="{Binding Y, Converter={StaticResource CoordToPixel}, ConverterParameter=50}" />
                
                <!-- 图片棋子示例,替换上面的Ellipse即可 -->
                <!-- <Image Source="{Binding PieceImage}" Width="40" Height="40"
                       Canvas.Left="{Binding X, Converter={StaticResource CoordToPixel}, ConverterParameter=50}"
                       Canvas.Top="{Binding Y, Converter={StaticResource CoordToPixel}, ConverterParameter=50}" /> -->
            </DataTemplate>
        </ItemsControl.ItemTemplate>
    </ItemsControl>
</Grid>

4. 实现坐标转像素的转换器

需要一个转换器把棋盘坐标(X/Y)转换成Canvas的像素位置,让棋子居中显示在格子里:

public class CoordToPixelConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value is int coord && int.TryParse(parameter.ToString(), out int cellSize))
        {
            // 计算居中位置:格子坐标*格子大小 + (格子大小-棋子大小)/2
            return coord * cellSize + (cellSize - 40) / 2;
        }
        return 0;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

别忘了在XAML的资源里注册这个转换器:

<Window.Resources>
    <local:CoordToPixelConverter x:Key="CoordToPixel" />
</Window.Resources>

这样改动后,你可以完全控制PlayerPieces集合的内容——初始只加4个,就只显示4个;后续游戏中添加/移除棋子,视图也会自动更新。棋子样式可以自由切换圆形或图片,视觉效果比改格子颜色好得多。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 15:15:46