нужна тут многопоточность?
От: Dancer Россия  
Дата: 30.03.02 14:41
Оценка:
Ситуация такая: есть двумерный массив точек, значения элементов массива изменяются в цикле функцией Evaluate. Я хочу выводить этот массив на экран после КАЖДОЙ итерации цикла. Если я правильно понимаю, то просто вариант
for(int i = 0;i < m_numOfIterations;i++)
{
Evaluate();
InvalidateRect(CRect(10, 10, 650, 650), FALSE);
}
не работает по причине буферизации вывода => картинка не успевает отрисоваться до начала следующей итерации цикла.
Я попробовал делать в цикле такую вещь:
for(...)
{
Evaluate();
InvalidateRect(CRect(10, 10, 650, 650), FALSE);
::WaitForSingleObject(g_eventFinished, INFINITE);
}
а из OnPaint класса СDialog активировать g_eventFinished (с автосбросом) после того, как все отрисуется, но почему-то не выходит.
Каково стандартное разрешение этой ситуации? Обязательно ли заводить отдельный поток (перенести в него вычисления или рисовать в нем)?
Re: нужна тут многопоточность?
От: Igor Soukhov  
Дата: 30.03.02 19:32
Оценка:
Здравствуйте Dancer, Вы писали:

D>Ситуация такая: есть двумерный массив точек, значения элементов массива изменяются в цикле функцией Evaluate. Я хочу выводить этот массив на экран после КАЖДОЙ итерации цикла. Если я правильно понимаю, то просто вариант

D>for(int i = 0;i < m_numOfIterations;i++)
D>{
D> Evaluate();
D> InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>}
D>не работает по причине буферизации вывода => картинка не успевает отрисоваться до начала следующей итерации цикла.
D>Я попробовал делать в цикле такую вещь:
D>for(...)
D>{
D>Evaluate();
D>InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>::WaitForSingleObject(g_eventFinished, INFINITE);
D>}
D>а из OnPaint класса СDialog активировать g_eventFinished (с автосбросом) после того, как все отрисуется, но почему-то не выходит.
D>Каково стандартное разрешение этой ситуации? Обязательно ли заводить отдельный поток (перенести в него вычисления или рисовать в нем)?
проводи вычисления во втором потоке и инициируй из него отрисовку.
* thriving in a production environment *
Re: нужна тут многопоточность?
От: Алекс Россия http://wise-orm.com
Дата: 30.03.02 22:39
Оценка:
Здравствуйте Dancer, Вы писали:

D>Ситуация такая: есть двумерный массив точек, значения элементов массива изменяются в цикле функцией Evaluate. Я хочу выводить этот массив на экран после КАЖДОЙ итерации цикла. Если я правильно понимаю, то просто вариант

D>for(int i = 0;i < m_numOfIterations;i++)
D>{
D> Evaluate();
D> InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>}
D>не работает по причине буферизации вывода => картинка не успевает отрисоваться до начала следующей итерации цикла.
D>Я попробовал делать в цикле такую вещь:
D>for(...)
D>{
D>Evaluate();
D>InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>::WaitForSingleObject(g_eventFinished, INFINITE);
D>}
D>а из OnPaint класса СDialog активировать g_eventFinished (с автосбросом) после того, как все отрисуется, но почему-то не выходит.
D>Каково стандартное разрешение этой ситуации? Обязательно ли заводить отдельный поток (перенести в него вычисления или рисовать в нем)?

Не выходит потому, что InvalidateRect() ничего не рисует и даже сообщений никаких не посылает. Она просто добавляет к окну регион, который надо перерисовать в WM_PAINT. Если ты хочешь, чтобы WM_PAINT вызывалась сразу (почти) — сделай UpdateWindow().
Re[2]: нужна тут многопоточность?
От: Dancer Россия  
Дата: 31.03.02 08:07
Оценка:
Здравствуйте Алекс, Вы писали:

А>Здравствуйте Dancer, Вы писали:


D>>Ситуация такая: есть двумерный массив точек, значения элементов массива изменяются в цикле функцией Evaluate. Я хочу выводить этот массив на экран после КАЖДОЙ итерации цикла. Если я правильно понимаю, то просто вариант

D>>for(int i = 0;i < m_numOfIterations;i++)
D>>{
D>> Evaluate();
D>> InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>>}
D>>не работает по причине буферизации вывода => картинка не успевает отрисоваться до начала следующей итерации цикла.
D>>Я попробовал делать в цикле такую вещь:
D>>for(...)
D>>{
D>>Evaluate();
D>>InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>>::WaitForSingleObject(g_eventFinished, INFINITE);
D>>}
D>>а из OnPaint класса СDialog активировать g_eventFinished (с автосбросом) после того, как все отрисуется, но почему-то не выходит.
D>>Каково стандартное разрешение этой ситуации? Обязательно ли заводить отдельный поток (перенести в него вычисления или рисовать в нем)?

А>Не выходит потому, что InvalidateRect() ничего не рисует и даже сообщений никаких не посылает. Она просто добавляет к окну регион, который надо перерисовать в WM_PAINT. Если ты хочешь, чтобы WM_PAINT вызывалась сразу (почти) — сделай UpdateWindow().


Странно, у меня в книжке написано, что (цитирую) "... код Invalidate" впоследствии вызовет OnDraw", но это про SDI, а тут по логике вещей должно вызываться OnPaint (я так думал).
Re[3]: нужна тут многопоточность?
От: Алекс Россия http://wise-orm.com
Дата: 01.04.02 04:11
Оценка:
Здравствуйте Dancer, Вы писали:

D>Здравствуйте Алекс, Вы писали:


А>>Здравствуйте Dancer, Вы писали:


D>>>Ситуация такая: есть двумерный массив точек, значения элементов массива изменяются в цикле функцией Evaluate. Я хочу выводить этот массив на экран после КАЖДОЙ итерации цикла. Если я правильно понимаю, то просто вариант

D>>>for(int i = 0;i < m_numOfIterations;i++)
D>>>{
D>>> Evaluate();
D>>> InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>>>}
D>>>не работает по причине буферизации вывода => картинка не успевает отрисоваться до начала следующей итерации цикла.
D>>>Я попробовал делать в цикле такую вещь:
D>>>for(...)
D>>>{
D>>>Evaluate();
D>>>InvalidateRect(CRect(10, 10, 650, 650), FALSE);
D>>>::WaitForSingleObject(g_eventFinished, INFINITE);
D>>>}
D>>>а из OnPaint класса СDialog активировать g_eventFinished (с автосбросом) после того, как все отрисуется, но почему-то не выходит.
D>>>Каково стандартное разрешение этой ситуации? Обязательно ли заводить отдельный поток (перенести в него вычисления или рисовать в нем)?

А>>Не выходит потому, что InvalidateRect() ничего не рисует и даже сообщений никаких не посылает. Она просто добавляет к окну регион, который надо перерисовать в WM_PAINT. Если ты хочешь, чтобы WM_PAINT вызывалась сразу (почти) — сделай UpdateWindow().


D>Странно, у меня в книжке написано, что (цитирую) "... код Invalidate" впоследствии вызовет OnDraw", но это про SDI, а тут по логике вещей должно вызываться OnPaint (я так думал).


MSDN: The invalidated areas accumulate in the update region until the region is processed when the next WM_PAINT message occurs or until the region is validated by using the ValidateRect or ValidateRgn function.

Читай доки на системные функции, а не на их обертки!
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.