Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Общие вопросы по .NET и C# > Затерается рисунок (С#)


Автор: Edd 4.3.2007, 20:43
Открываю bmp, рисую его в picturBox.
Вроде всё хорошо, но если на рисунок навести другой обьект или свернуть форму,
 то ресунок пропадает( стирается).
Как эту проблему решить? Ниже приведон код.
Код

private void button1_Click(object sender, EventArgs e)
        {
            String FName;
            if (openFileDialog1.ShowDialog() == DialogResult.OK)
            {
                FName = openFileDialog1.FileName.ToString();
                Bitmap ImageOpen = new Bitmap(FName);
                Graphics g = pictureBox1.CreateGraphics();
                pictureBox1.Width = ImageOpen.Width;
                pictureBox1.Height = ImageOpen.Height;
                Rectangle RectIn = new Rectangle(0, 0, ImageOpen.Width, ImageOpen.Height);// куда рисуем 
                Rectangle RectOut = new Rectangle(0, 0, ImageOpen.Width, ImageOpen.Height);//откуда рисуем
                g.DrawImage(ImageOpen, RectIn, RectOut, GraphicsUnit.Pixel);
                g.Dispose();
                ImageOpen.Dispose();
            }
        }

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

Автор: Void 4.3.2007, 20:54
В данном конкретном случае можно просто установить свойство PictureBox.Image.

А вообще, чтобы избежать затирания, надо обрабатывать событие Paint.

Автор: Edd 4.3.2007, 21:24
C PictureBox.Image: в смысле на прямую загружать рисунок? Но мне надо будет вырезать куски рисунка.

А как обрабатывать событие Paint?  smile (По форуму ускал, ничего не нашол)

Автор: Idsa 4.3.2007, 22:05
Цитата(Void @  4.3.2007,  20:54 Найти цитируемый пост)
А вообще, чтобы избежать затирания, надо обрабатывать событие Paint.

Нее, обрабатывать OnPaint - не дело: для этого нужно хранить координаты всех нарисованных фигур. На мой взгляд, лучше делать вот так:
Код

string fileName = "image.bmp";
pictureBox1.Image = new Bitmap(fileName);
Graphics g = Graphics.FromImage(pictureBox1.Image);
g.DrawLine(Pens.Aqua, new Point(0, 0), new Point(10, 10));

В этом случае нарисованное тобой не стирается и перерисовкой заниматься не нужно.

Цитата(Edd @  4.3.2007,  21:24 Найти цитируемый пост)
А как обрабатывать событие Paint?

Делаешь обработчик события Paint в PictureBox:
Код

private void pictureBox1_Paint(object sender, PaintEventArgs e)
    {
      Graphics g = e.Graphics;
      g.DrawLine(Pens.Aqua, new Point(0, 0), new Point(10, 10));
    }

(делает код то же, что и в примере выше).

А вообще, я так и не разобрался во внутренностях этого процесса: почему так по-разному ведут себя рисунки при получении Graphics разными способами. Буду очень благодарен за ссылочки или подробное объяснение.

Автор: mr.DUDA 4.3.2007, 22:12
Цитата(Edd @  4.3.2007,  20:24 Найти цитируемый пост)
А как обрабатывать событие Paint?

В property grid у pictureBox1 на закладке Events надо дважды кликнуть в строке с Paint.

Автор: Edd 5.3.2007, 16:25
Используя:
Код

Graphics g = Graphics.FromImage(pictureBox1.Image);
g.DrawImage(ImageOpen, RectIn, RectOut, GraphicsUnit.Pixel);

затерание пропадает, но этот метод нельзя применять если
pictureBox1.Image=null;,
А мне надо использовать куски рисунков, которые могут быть разных форматов и в этом pictureBox1 рисовать.

П.С. Есть ли возможность к загружонному ресунку ислпользовать Transparent(Прозрачность фонового цвета).

Автор: -Mikle- 6.3.2007, 14:50
Расскажи что ты вообще делаешь, а то тут предлагают всякого разного, опиши свою задачу, и тебе помогут грамотно реализовать ее. Что ходить вогруг, да около. Лично мне показалось что ты делаешь двумерную игрушку. И я мог бы рассказать как и что лучше сделать с прорисовкой, но вдруг я ошибся, и выйдет что я зря потратил время.

Автор: Edd 8.3.2007, 18:05
Делаю следующее: небольшая программка по обработке граффики.

Создаётся массив pictureBox-сов, в эти pictureBox-ы (PB) пользователь грузит картинки, разных размеров и форматов. Хотя не в PB, а в массив Bitmap-ов. PB нужны чтобы с картинками работать: отаброжать, перемещать по форме.
Далее, когда всё загружено и раставлено, всё это рисуется в отдельном pictureBox-се с соответствующими координатами. Полученное новое изображение сохраняется.

Проблема: Прорисовки всего (всех загруженных картинок) на отдельном pictureBox-се. С загрузкой, размещением и определением какую часть рисунка рисовать, проблем нету.

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

Мозет для всего этого использовать другую компоненту, вместо pictureBox, или вообще свою создать?

Автор: mr.DUDA 9.3.2007, 12:23
Уж не проще ли тогда рисовать все битмапы в одном контроле, например на панели ?

Автор: -Mikle- 9.3.2007, 16:15
Ну тогда все просто:

Код

Bitmap[] bmps = ...; // все картинки, к примеру взял массив, но это не принципиально
Bitmap destination = new Bitmap(w, h); // w и h - размеры конечной картинки, то есть твоего PB или Panel

private void UpdateBitmap()
{
    Graphics g = Graphics.FromImage(destination); // создаем Graphics для destination
    g.Clear(Color.Black); // заливаем всю область нужным цветом фона

    // рисуем поочередно все картинки в координатах x y
    for(int i=0; i<bmps.Length; i++)
        g.DrawImageUnscaled(bmps[i], x, y);

    g.Dispose(); // уничтожаем Graphics после того, как он не нужен
}


// использование вариант №1 
        pictureBox1.BackgroundImageLayout = ImageLayout.None;
        pictureBox1.BackgroundImage = destination;
        // или
        pictureBox1.Image = destination;


// использование вариант №2

        // функция обработки события Paint того контрола, на котором ты хочешь рисовать все
        private void pictureBox1_Paint(object sender, PaintEventArgs e)
        {
            // если картинка destination изменилась, то надо перерисовать ее
            // здесь я просто для примера придумал свое название переменной, замени его на любое свое
            if( updateBitmapNeeded )
                UpdateBitmap();

            // рисуем картинку прям на контроле
            e.Graphics.DrawImageUnscaled(destination, 0, 0);
        }



Здесь код приведен в стиле "для ознакомления с принципом работы". В конечном коде необходимы различного рода оптимизации.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)