C# 使平滑动画c的区域无效#

C# 使平滑动画c的区域无效#,c#,animation,graphics,region,invalidation,C#,Animation,Graphics,Region,Invalidation,我正在做一个关于象棋类游戏的项目,因此玩家在地图上拥有自己的棋子。每当玩家决定移动一个棋子时,他需要从骰子中获得一个数字,然后该棋子将根据滚动的数字移动。典当的移动功能已经完成,但我没有为他们展示移动过程 我有一个地图面板和四个起始基地面板(在游戏开始时拿着棋子)。 在绘制事件中,我要求系统绘制所有内容 private void P_Map_Paint(object sender, PaintEventArgs e) { manager.VisualizeCol

我正在做一个关于象棋类游戏的项目,因此玩家在地图上拥有自己的棋子。每当玩家决定移动一个棋子时,他需要从骰子中获得一个数字,然后该棋子将根据滚动的数字移动。典当的移动功能已经完成,但我没有为他们展示移动过程

我有一个地图面板和四个起始基地面板(在游戏开始时拿着棋子)。

在绘制事件中,我要求系统绘制所有内容

private void P_Map_Paint(object sender, PaintEventArgs e)
    {
            manager.VisualizeCollection(map, gr_map);
            manager.VisualizeStartingBase(bases, grs); 
            manager.VisualizePawns(manager.Players, grs, gr_map);
            manager.DisplayAvailablePawn(gr_map, grs);
            manager.DisplaySelectedPawn(gr_map, grs);
    }
对于棋子的每一个动作,我都试图使用计时器使图像在屏幕上移动

public void DoMovement(Pawn pawn)
    {
        if (TargetSpot != null)
        {
            System.Windows.Forms.Timer t = new System.Windows.Forms.Timer();
            EventHandler t_tick = null;
            Point targetP = TargetSpot.Location;
            Point currentP = pawn.ImageLocation;
            int XMove = (targetP.X - currentP.X) / 10;
            int YMove = (targetP.Y - currentP.Y) / 10;

            Rectangle drawRange = new Rectangle(pawn.ImageLocation.X - (int)(0.5 * pawn.Image.Width),
                                                pawn.ImageLocation.Y - (int)(0.5 * pawn.Image.Height), pawn.Image.Width, pawn.Image.Height);
            t_tick = (senders, args) =>
            {
                if (currentP.X > targetP.X - XMove || currentP.X < targetP.X + XMove)
                {// if the image of the pawn doesn't reach the destination
                    //we keep moving it and ask the pawn to redraw the old place
                    pawn.ImageLocation = new Point(currentP.X + XMove, currentP.Y + YMove);
                    pawn.CurrentPanel.Invalidate(drawRange);
                }
                else
                {
                    pawn.CurrentLocation.LeaveAPawn(pawn);
                    pawn.CurrentLocation = TargetSpot;
                    TargetSpot.AddAPawn(pawn);
                    pawn.CurrentPanel.Invalidate(drawRange);
                }
            };
            t.Tick += t_tick;
            t.Interval = 300;
            t.Start();
        }
    }
公共无效移动(典当)
{
if(TargetSpot!=null)
{
System.Windows.Forms.Timer t=新的System.Windows.Forms.Timer();
EventHandler t_tick=null;
点targetP=目标点位置;
点电流P=典当图像位置;
int XMove=(targetP.X-currentP.X)/10;
int YMove=(targetP.Y-current p.Y)/10;
矩形drawRange=新矩形(pawn.ImageLocation.X-(int)(0.5*pawn.Image.Width),
pawn.ImageLocation.Y-(int)(0.5*pawn.Image.Height)、pawn.Image.Width、pawn.Image.Height);
t_tick=(发送者、参数)=>
{
if(currentP.X>targetP.X-XMove | | currentP.X
这不是很好,面板上的所有内容仍在重新绘制。为什么?


除了这个项目,我确实有一个关于区域无效的问题。就像我告诉画画规则一样,画板会自动失效。当我们要使一个区域失效时,系统是如何知道绘图规则的?

我不是100%确定,但我非常确定,每次调用
domove
时,都会创建一个新的计时器,并每隔300毫秒触发一次,因为您从不调用stop。这可能会给你一些奇怪的结果。因此,在5次移动之后,您有5个计时器在运行。a)如果您希望避免过度重新绘制,可以使矩形区域无效;请注意,对于国际象棋移动,这必须包括旧位置和新位置。通常没有大的收获。b) TyCobb关于计时器的说法可能是对的c)计时器每秒只移动3帧,这对于动画来说有点慢。d) 好奇:你不会把e.Graphics对象发给你的经理。为什么?正确的绘图需要它。动画可以不用…谢谢两个人的帮助,我现在有了更多的进步!TaW,实际上我已经通过了图形:)gr_地图和grs是图形。它们在方法内部使用