Форум: "WinAPI";
Текущий архив: 2018.04.22;
Скачать: [xml.tar.bz2];
ВнизМетафайлы тормозят при ресайзе Найти похожие ветки
← →
ProgRAMmer Dimonych © (2010-09-30 21:46) [0]Пишу "графический редактор" с использованием HENHMETAFILE"ов. Для рисования создаю отдельный класс окна. Всё рисование производится одновременно в memory bitmap (hDC+hBitmap) и метафайл (hMFDC). Битмап используется для быстрой отрисовки окна, метафайл - для хранения собственно действий, приводящих к получению изображения.
Добавляю обработку WM_SIZE, выполняю следующие действия:
1. Пересоздаю битмап в памяти (разумеется, с отсоединением и последующим присоединением к hDC).
2. hMF:=CloseEnhMetaFile(hMFDC)
3. hMFDC:=CreateEnhMetaFile(...)
4. PlayEnhMetaFile() в hDC и hMFDC.
5. DeleteEnhMetaFile(hMF)
6. Перерисовка окна.
При многократных ресайзах наблюдаю постепенное замедление процесса: после 2-3 десятков ресайзов (независимо от того, увеличение или уменьшение) обработка WM_SIZE начинает занимать несколько секунд.
Все метафайлы создаются в памяти, без привязки к файлам на диске.
Сталкивался ли кто-нибудь с такой проблемой?
← →
Дмитрий Тимохов 2 (2010-10-01 00:02) [1]пользуюсь метафайлами регулярно.
ты бы код привел, воспроизводивший проблему...
← →
ProgRAMmer Dimonych © (2010-10-01 01:10) [2]На сях он, правда :)
SelectObject(pbs->hdcMem,pbs->hbmMemO);
DeleteObject(pbs->hbmMem);
hdc = GetDC(hWnd);
pbs->hbmMem = CreateCompatibleBitmap(hdc,wr.right,wr.bottom);
SelectObject(pbs->hdcMem,pbs->hbmMem);
ReleaseDC(hWnd,hdc);
FillRect(pbs->hdcMem,&wr,pbs->hbrBack);
hMF = CloseEnhMetaFile(pbs->hMFDC);
pbs->hMFDC = PaintBox_CreateMetaFile(pbs,NULL,&wr);
PlayEnhMetaFile(pbs->hMFDC,hMF,&wr);
PlayEnhMetaFile(pbs->hdcMem,hMF,&wr);
DeleteEnhMetaFile(hMF);
InvalidateRect(hWnd,NULL,FALSE);
UpdateWindow(hWnd);
pbs - это указатель на структуру с хэндлами, коорднатами и прочей внутриклассовой ересью.
pbs->hbmMemO - то, что вернула SelectObject() при привязке битмапа к DC
wr - структура RECT, результат выполнения GetClientRect()
pbs->hMFDC - DC, полученный при вызове CreateEnhMetaFile()HDC PaintBox_CreateMetaFile(PPaintBoxStruct pbs, TCHAR lpFileName[], const LPRECT rect)
{
int iWidthMM, iHeightMM, iWidthPels, iHeightPels;
RECT tr;
if (rect == NULL)
return CreateEnhMetaFile(pbs->hdcMem,lpFileName,NULL,NULL);
iWidthMM = GetDeviceCaps(pbs->hdcMem,HORZSIZE);
iHeightMM = GetDeviceCaps(pbs->hdcMem,VERTSIZE);
iWidthPels = GetDeviceCaps(pbs->hdcMem,HORZRES);
iHeightPels = GetDeviceCaps(pbs->hdcMem,VERTRES);
tr = *rect;
tr.left = (tr.left * iWidthMM * 100) / iWidthPels;
tr.top = (tr.top * iHeightMM * 100) / iHeightPels;
tr.right = (tr.right * iWidthMM * 100) / iWidthPels;
tr.bottom = (tr.bottom * iHeightMM * 100) / iHeightPels;
return CreateEnhMetaFile(pbs->hdcMem,lpFileName,&tr,NULL);
}
Собственно, это и весь код, который выполняется при ресайзе. Просто ресайзить достаточно, чтобы накапливались тормоза, никаких рисований дополнительно не требуется.
← →
han_malign (2010-10-11 17:24) [3]уверен что pbs->hbmMemO != NULL?
попробуй DeleteObject(SelectObject(pbs->hdcMem,pbs->hbmMem));
← →
ProgRAMmer Dimonych © (2010-10-26 21:36) [4]Выкроил наконец-то время.
pbs->hbmMemO != NULL, гарантированно. Отладчик не врёт, SelectObject() возвращает корректный хэндл, равный сохранённому ранее в pbs->hbmMem. Удаление происходит корректно.
С OllyDbg в зубах выяснил, что утечка происходит при отрисовке PlayEnhMetaFile(), причём, похоже, только тогда, когда отрисовка идёт в DC нового метафайла. При отрисовке в обычный DC утечек, похоже, нет.
Кроме того, сделав EnumEnhMetaFile() и поставив бряк в callback-функции, выяснил, что уже при первой отрисовке помимо мелочей вроде SetBkColor() в DC нового метафайла отрисовывается всякая экзотика вроде TextOut() и RoundRect(), хотя ничего подобного в исходном метафайле не было.
Из упоминаний утечек нарыл только про утечку в Win9x, но конкретно у меня сейчас проблема в WinXP, а по ней замечаний гугл не даёт. :(
← →
ProgRAMmer Dimonych © (2010-10-28 01:04) [5]Наткнулся на краткое упоминание про утечку в остальных системах. Но ответа на вопрос, как этого избежать, там, к сожалению, нет. А тормоза и правда ощутимые. :(
Страницы: 1 вся ветка
Форум: "WinAPI";
Текущий архив: 2018.04.22;
Скачать: [xml.tar.bz2];
Память: 0.47 MB
Время: 0.001 c