Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > .NET Frameworks (точка нет фреймворки) > C# (си шарп)
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 21.03.2012, 14:39   #1
Lime
Форумчанин
 
Аватар для Lime
 
Регистрация: 10.02.2009
Сообщений: 815
Вопрос Отключить перерисовку элемента

Доброго времени суток!
В событии панели OnPaint() создана длительная анимация, останаилвается основной поток:
Код:
System.Threading.Thread.Sleep(n);
При этом windows или что-то ещё инициирует перерисовку панели до того как закончилась анимация, в следствии чего windows считает что программа зависла.

В Delphi была такая замечательная штука:
Код:
Application.ProcessMessages;
которая между sleep'ами обрабатывала приходящие сообщения и программа считалась "нормально работающей".

Собственно вопрос заключается в том, как отключить перерисовку panel'и извне в С#, либо обрубать сообщения в событии, либо чистить "стэк" от него, в общем хочу чтобы моя "быстрая" или "долгая" анимация доходила до конца.

p.s. пробовал Application.DoEvents(); не уверен что в след раз "сработает" т.к. зависания показались рандомными.

Спасибо!

Последний раз редактировалось Lime; 21.03.2012 в 16:50.
Lime вне форума Ответить с цитированием
Старый 21.03.2012, 15:41   #2
ds.Dante
Старожил
 
Аватар для ds.Dante
 
Регистрация: 06.08.2009
Сообщений: 2,992
По умолчанию

Во-первых, можно запретить заходить в OnPaint одновременно два раза.

Код:
volatile bool painting = false;
void OnPaint ()
{
	if (painting)
		return;
	painting = true;
	try
	{
		...
	}
	finally
	{
		painting = false;
	}
}
А чтобы последняя отрисовка не пропадала, можно сделать чуть сложнее: при втором входе программа встаёт в lock, а при третьем - просто return.

Во-вторых, делать длительные операции в OnPaint как-то неправильно. Лучше вызвать их асинхронно, а в конце операции вызвать Invalidate ().
ds.Dante вне форума Ответить с цитированием
Старый 21.03.2012, 16:46   #3
Lime
Форумчанин
 
Аватар для Lime
 
Регистрация: 10.02.2009
Сообщений: 815
По умолчанию

Цитата:
Сообщение от ds.Dante Посмотреть сообщение
Во-первых, можно запретить заходить в OnPaint одновременно два раза.
По факту в OnPaint() то заходит, несмотря на то что там пусто. У меня так и сделано
Код:
if (animate)

Цитата:
вызвать их асинхронно
если тут был линк - то он битый.
Да, я бы смог сделать всё по другому, но меня интересует именно выход из этой ситуации.

Последний раз редактировалось Lime; 21.03.2012 в 16:49.
Lime вне форума Ответить с цитированием
Старый 21.03.2012, 17:01   #4
ds.Dante
Старожил
 
Аватар для ds.Dante
 
Регистрация: 06.08.2009
Сообщений: 2,992
По умолчанию

Ого ж как мой пост переглючило... Я сделал ссылку на ThreadPool.QueueUserWorkItem, потому что все почему-то создают Thread, даже для простейших случаев.

Прочитал вопрос ещё раз, и понял, что ничего не понял. Без кода понять трудно.
ds.Dante вне форума Ответить с цитированием
Старый 21.03.2012, 18:20   #5
Lime
Форумчанин
 
Аватар для Lime
 
Регистрация: 10.02.2009
Сообщений: 815
Подмигивание

В коде ничего особенного, пара циклов да рисование примитивных фигур, и всё это в OnPaint() панельки.
Вложения
Тип файла: zip HeapSort.zip (43.0 Кб, 11 просмотров)
Lime вне форума Ответить с цитированием
Старый 22.03.2012, 09:07   #6
ds.Dante
Старожил
 
Аватар для ds.Dante
 
Регистрация: 06.08.2009
Сообщений: 2,992
По умолчанию

Я имел в виду исходный код, а не бинарник.

Цитата:
Сообщение от Lime Посмотреть сообщение
Да, я бы смог сделать всё по другому, но меня интересует именно выход из этой ситуации.
Засовывать Sleep в OnPaint - порочная практика. Асинхронные операции для того и существуют, чтобы выполнять их, не блокируя UI.

Последний раз редактировалось ds.Dante; 22.03.2012 в 09:16.
ds.Dante вне форума Ответить с цитированием
Старый 22.03.2012, 16:13   #7
Lime
Форумчанин
 
Аватар для Lime
 
Регистрация: 10.02.2009
Сообщений: 815
По умолчанию

Цитата:
Сообщение от ds.Dante Посмотреть сообщение
Я имел в виду исходный код, а не бинарник.


Засовывать Sleep в OnPaint - порочная практика. Асинхронные операции для того и существуют, чтобы выполнять их, не блокируя UI.
На счет исходников - я понял, просто показал программу.
Задача была - сделать анимацию работы алгоритма. Нечто вроде этого:
(на картинке построение, равносильно 0-вому проходу цикла сортировки)

При этом анимацию довольно удобно делать в самом коде алгоритма, т.к. от программы не требуется сама сортировка и её быстрое выполнение. А отдельный поток для вызова перерисовки делать не хотелось, к тому-же я не до конца разобрался с дескрипторами и рисованием без вывода изображения на какой-либо элемент.
Lime вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Отключить регистрацию Predator199 PHP 0 06.03.2012 06:22
Запретить перерисовку TChart Sanprof Общие вопросы Delphi 3 25.11.2011 11:29
отключить в TWebBrowser.... designer999 Работа с сетью в Delphi 0 10.05.2010 10:56
можно ли прописать стиль для элемента "внутри" этого самого элемента ? vedro-compota HTML и CSS 8 03.05.2010 17:24
Си -Расположить элементы в порядке возрастания от первого нулевого элемента до отрицательного элемента Freia Помощь студентам 17 13.12.2009 15:41