Обновление свойства изображения объекта каждый таймер C # - PullRequest
0 голосов
/ 13 ноября 2011

У меня есть класс спрайта, у которого есть метод draw, который рисует взрыв.У класса есть свойство image, которое используется как изображение, которое будет нарисовано.

Я хочу, чтобы оно было таким, чтобы рисованное изображение менялось каждые 5 секунд или около того.

Мой вопрос: используя элемент управления таймером, как я могу его закодировать, чтобы свойство Image менялось на другое изображение каждый тик?

Например, изображение 1 «5 секунд»> изображение 2 «5 секунд»> изображение 3 «5 секунд»> удалить изображение.

Вот метод рисования:

    public void DrawExplosion(Graphics graphics)
    {
        graphics.DrawImage(explosion_, xPos_, yPos_);
    }

и свойство Image класса

    public Image Explosion
    {
        get {return explosion_;}
        set {explosion_ = value;}
    }

Спасибо за любую помощь / руководство.

Ответы [ 3 ]

1 голос
/ 17 ноября 2011

Я заметил, что мой ответ был слишком сложным для простого вопроса.Хотя я не верю, что это неправильно, я думаю, что это усложняет ситуацию.Я хотел оставить это там на тот случай, если кто-то еще посчитает это полезным.Но вот упрощенная попытка.Он использует таймер, внешний по отношению к классу Sprite, кнопку и панель.Я надеюсь, что это полезно.

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace CustomControl
{
public partial class Form1 : Form
{
    Sprites Explosion = new Sprites();


    public Form1()
    {
        InitializeComponent();
        //insert your images in this next line
        Explosion.Images=new Image[]{Properties.Resources.explode1,Properties.Resources.explode2,Properties.Resources.explode3};
        Explosion.ImageIndex = 0;
    }

    private void button1_Click(object sender, EventArgs e)
    {
        timer1.Enabled = true;
        //Draw the first image right away
        Explosion.Draw(panel1.CreateGraphics(), 0, 0);
        //set the index to the next image
        Explosion.ImageIndex++;
    }


    private void timer1_Tick(object sender, EventArgs e)
    {
        //if the Imageindex is not greater then the number of images
        if (Explosion.ImageIndex < Explosion.Images.Count() )
        {
            Explosion.Draw(panel1.CreateGraphics(), 0, 0);
            Explosion.ImageIndex++;
        }
        //if it is greater then reset the imageIndex and turn off the timer
        else
        {
            Explosion.ImageIndex = 0;
            timer1.Enabled = false;
            //Clear your images, however you need to do that
            panel1.CreateGraphics().Clear(Color.White);
        }


    }
}


public class Sprites
{
    public Image DisplayedImage { get { return Images[ImageIndex]; } }
    public int ImageIndex;
    public Image[] Images;

    public void Draw(Graphics graphics, int x, int y)
    {
        graphics.DrawImage(DisplayedImage, x, y);
    }


}

}
0 голосов
/ 17 ноября 2011

РЕДАКТИРОВАТЬ: я добавил еще один ответ ниже. Я нашел этот ответ сложным для заданного вопроса.

JRoughan Может быть, есть и лучшие способы сделать это. Но по вашему запросу я написал класс, который будет принимать изображения, которые вы предоставляете, и рисовать их по одному на графический объект, а затем очищать графический объект.

Я создал экземпляр класса в методе, поэтому нет никакой гарантии, что он не выйдет из области видимости и не будет собран до полного запуска, чтобы избежать этого, вы можете сделать его глобальным, а затем просто создавать его каждый раз, когда захотите использовать его, с новыми изображениями. Но если вы вызовете его дважды, первым будет потеря, поэтому я нашел этот метод лучше, это зависит от контекста, количества различных анимаций, которые вы планируете использовать одновременно и т. Д. Я также добавил событие ImageindexChanged, которое может использоваться, чтобы знать, когда изображение меняется за пределами класса. Наслаждайтесь! Я надеюсь, что это то, что вы ищете.

Я только что добавил кнопку и панель. связывая событие нажатия кнопок в метод Button1_Click

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace CustomControl
{
public partial class Form1 : Form
{

    public Form1()
    {
        InitializeComponent();
        //insert your images in this next line
    }

    private void button1_Click(object sender, EventArgs e)
    {

        Image[] explodingImages = new Image[] { Properties.Resources.explode1, Properties.Resources.explode2, Properties.Resources.explode3 };
        //initialize the explosion with the images from above
        Sprites Explosion = new Sprites(explodingImages,panel1.CreateGraphics());
        //the timer will start and it will draw all images from the above collection, then clear itself, then dispose of itself.
        Explosion.ImageIndex = 0;
    }

}


public class Sprites
{
    private Image _DisplayedImage;
    public Image DisplayedImage
    {
        get { return _DisplayedImage; } 
    }
    private Image[] Images{get;set;}
    private int _ImageIndex = 0;

    public event EventHandler ImageIndexChanged;

    public int ImageIndex
    {
        get { return _ImageIndex; }
        set
        {
            //Changes thh ImageIndexNumber
            _ImageIndex = value;
            //Updates the Displayed Image with the current Image as per index
            _DisplayedImage = Images[ImageIndex];
            //fires the ImageIndexChanged Event (if required)
            if (ImageIndexChanged != null)
                ImageIndexChanged(this, EventArgs.Empty);
            //draws the explosion to the graphics object
            DrawExplosion(G, 0, 0);
            //starts the timer
            changeImageTimer.Enabled = true;
        }
    }
    //local variable for the graphics object
    private Graphics G;
    //creats a timer for changing the Images
    Timer changeImageTimer = new Timer();
    //Constructor
    public Sprites(Image[] images,Graphics g)
    {
        //set the starting Images
        Images = images;
        //set the interval time to 5 seconds- in my opinion this number is rediculously high, but if that is what you want
        changeImageTimer.Interval = 5000;
        //Get the Tick event of the timer
        changeImageTimer.Tick += new EventHandler(changeImageTimer_Tick);
        //set the Graphics that you want to draw on
        G = g;
    }

    void changeImageTimer_Tick(object sender, EventArgs e)
    {
        int temp=ImageIndex+1;
        //if there are no more pictures to display stop the timer
        if (temp > Images.Count() - 1)
        {
            //stop the timer
            changeImageTimer.Enabled = false;
            //Clear the image, replace with your own background color, or draw an image or whatever you need to do to clear the images
            G.Clear(Color.White);
        }
        //if there are more pictures select the next picture
        else
            //Changeing the imageindex fires the draw method and the imageindexchanged event
            ImageIndex++;
    }

    public void DrawExplosion(Graphics graphics,int x, int y)
    {
        graphics.DrawImage(DisplayedImage, x, y);
    }
}
}
0 голосов
/ 14 ноября 2011

Если мои предположения верны и вы пишете игру, то вам, вероятно, здесь не нужен таймер.Есть много статей о программировании игровых циклов, которые бы подходили для вашего сценария.

Они в основном отделяют логическое обновление ваших элементов экрана (здесь, спрайта) от их рендеринга и используют хуки ОС для поддержания высокой производительности.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...