ExplodeMan |
Отправлено: 26.07.2005, 20:49 |
|
Ученик-кочегар
Группа: Участник
Сообщений: 18
|
Делаю прогу для отображения некоего графика( использую для этого компонент Chart). Данные приходят на com порт от одной железки и должны отображаться на графиках(ток, напряжение).
Для сбора этих данных используется отдельный поток, задача которого-обработать инфу и выдать ее графики....
//-----------------
Все работает отлично, но есть одно НО:
В случае, если открыто еще одно окно программы(FormX->showModal())
и это окно схвачено мышью за заголовок окна, программа "застывает" и графика не отображается....
такой глюк есть только в win98
//-----------------
мужики, кто знает, как эту хрень побороть?
|
|
Георгий |
Отправлено: 26.07.2005, 21:40 |
|
Почетный железнодорожник
Группа: Модератор
Сообщений: 874
|
данных маловато..
связь потока данных с железки с TChart как делаешь? |
|
Doga |
Отправлено: 26.07.2005, 21:42 |
|
Мастер участка
Группа: Участник
Сообщений: 575
|
Похоже две копии програмы одновременно пытаются работать с оодним устройством, мешая при этом друг другу. Заблокируйте запуск второй копии.
|
|
ExplodeMan |
Отправлено: 27.07.2005, 13:07 |
|
Ученик-кочегар
Группа: Участник
Сообщений: 18
|
2Георгий
отдельный поток работает примерно так:
//---------------------------------------------------------------------------------
void __fastcall RS232::Execute()
{
......... //действия перед началом работы потока
FreeOnTerminate=true;
do
{
SetCommMask(handle,EV_RXCHAR);
WaitCommEvent(handle,&mask,&Overlap);
//
//ждем событие "пришёл байт в буфер"
//
........ //запуск подпрограмм обработки полученных данных
Synchronize( GrPaint ); //рисуем графики в основном потоке программы
} while(!Terminated); //вечный цикл, пока вып-ся нить
........... //действия по окончанию работы потока
}
//---------------------------------------------------------------------------------
Все работает четко...
2Doga
запуск второй копии заблокирован.....
А вообще, под 98 виндозой сталкивался с аналогичной проблемой:
1)допустим, есть программа, состоящая из 1 формы.
на форме есть 2 компонента: TTimer и TLabel
2)ставим Timer1->Interval=1000;
3) по событию OnTimer включается/выключается Label:
void __fastcall TForm1::Timer1Timer(TObject *Sender)
{
Label1->Enabled=!Label1->Enabled;
}
3) запускаем Timer1->Enabled=true;
Что видим? раз в секунду надпись включается/выключается....
4) хватаем форму за заголовок мышью. Что видим? надпись больше не "шевелится"....
5)запускаем ту же прогу на ВинXP, выполняем пункт №4. Хотя форма и "схвачена", надпись все так же продолжает сигнализировать о том, что СОБЫТИЕ таймера наступило вовремя.......
тут, видимо, та же проблема....
|
|
Георгий |
Отправлено: 27.07.2005, 23:00 |
|
Почетный железнодорожник
Группа: Модератор
Сообщений: 874
|
QUOTE (ExplodeMan @ 27/07/2005, 14:07) | 2Георгий
Synchronize( GrPaint ); //рисуем графики в основном потоке программы |
ну тут всё очевидно — нет развязки по времени между потоком обмена с железкой и основным потоком.
будут у тебя и данные по ком порту теряться и обработка сообщений тормозиться и т.п.
пусть у тебя железячный поток кидает данные в промежуточный буфер (FiFo обрамлённый семафорами), а основной поток по таймеру разгребает этот буфер и гонит на визуализацию, да ещё и с двойной буферизацией изображение. причём разгребает буфер не блокируя его на долго на семафорах — т.е. заблокировал, скопировал мааааленький кусочек в локальный буфер, разблокировал, погнал на визуализацию, и так далее. |
|
ExplodeMan |
Отправлено: 28.07.2005, 10:02 |
|
Ученик-кочегар
Группа: Участник
Сообщений: 18
|
Георгий, данные не теряются- проверяно. Хотя предложенный тобой вариант мне нравится и если я совсем зайду в тупик то перепишу так, как ты советуешь.... Но как я ПО ТАЙМЕРУ буду разгребать фифо, если ОнТаймер не срабатывает под вин98 при вышеописанных обстоятельствах???? Вот в чем главная проблема и как ее решить пока не понял. Можно, конечно, в описалове проги написать "работает только под нт/хп" но это же не профессионально
|
|
Георгий |
Отправлено: 28.07.2005, 22:16 |
|
Почетный железнодорожник
Группа: Модератор
Сообщений: 874
|
против лома нет приёма..
когда делал нечто аналогичное то никаких проблем не замечал, правдо всё это работало под WinME, но тестики гонял и под 98 и под 95
зато как только пользователь отпустит окошко (перестанет тащить) никакие данные не потеряются, протокол обена с железкой не собьётся и всё корректно отрисуется
а может сделать главную форму невидимой, а пользователю показывать только вторичные — как помню в каждом окне свой цикл приёма сообщений, и если умная виндовая функция заблокирует работу цикла на время перетаскивания, то другие окна, в том числе и невидимое главное, будут жить. тогда в главной ловим таймер и всё делаем. и даже чарт, быть может перерисовываться будет.
PS. удивительно что данные по порту не теряются — по идее винда делает буфер всего на 2-4 кб, а как он заполнится, то все остальные посылки по RS откидываются
Отредактировано Георгий — 28/07/2005, 23:18 |
|
ExplodeMan |
Отправлено: 29.07.2005, 10:03 |
|
Ученик-кочегар
Группа: Участник
Сообщений: 18
|
QUOTE (Георгий @ 28/07/2005, 22:16) | а может сделать главную форму невидимой, а пользователю показывать только вторичные — как помню в каждом окне свой цикл приёма сообщений, и если умная виндовая функция заблокирует работу цикла на время перетаскивания, то другие окна, в том числе и невидимое главное, будут жить. тогда в главной ловим таймер и всё делаем. и даже чарт, быть может перерисовываться будет.
|
хорошая идея! сейчас буду пробовать!
|
|