Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > C/C++: Системное программирование и WinAPI > Утечка памяти


Автор: leopard678 17.11.2006, 16:52
Что приводит к утечке памяти?

Код

void CSimpleButton::Draw(HDC pDC)
{
    dcMem1 = CreateCompatibleDC(pDC);

    //--выбор изображения кнопки
    switch(m_iState) 
    {
        case 0:
            {
                 SelectObject(dcMem1,m_hbBMP_Disable);
                break;
            }
        case 1:
            {
                SelectObject(dcMem1,m_hbBMP_Normal);
                break;
            }
        case 2:
            {
                SelectObject(dcMem1,m_hbBMP_HighLight);
                break;
            }
        case 3:
            {
                SelectObject(dcMem1,m_hbBMP_Push);
                break;
            }        
        default:   // если значение состояния вне допустимого - ничего не рисуем
            {

                break;
            }        
    }
    BitBlt(pDC,m_iX,m_iY,m_iCX,m_iCY,dcMem1,0,0,SRCCOPY);

    ::DeleteDC(dcMem1);

}

Автор: leopard678 17.11.2006, 17:19
Если вместо BitBlt(pDC,m_iX,m_iY,m_iCX,m_iCY,dcMem1,0,0,SRCCOPY);
использовать:
Код

COLORREF clSrc;
    for(int x=0; x<nWidth; x++)
        for(int y=0; y<nHeight; y++)
        {
        
            // получаем цвет пикселя источника
            clSrc=GetPixel(hdcSrc,nXSrc+x,nYSrc+y);            
            // если цвет источника не соответствует цвету прозрачности...
        //    if(clSrc!=ColorX) 
        //    {    //...то меняем пиксель в приёмнике
                SetPixel(hdcDest, nXDest+x, nYDest+y, clSrc);
        //    }
            
        } 


то утечки нет, но работает медленней... smile 

Автор: JackYF 17.11.2006, 17:44
Как ты определяешь утечку? И где конкретно она происходит?

Автор: leopard678 17.11.2006, 17:50
Я её вижу в диспетчере задач  Windows ...
если вношу изменения описанные выше...то её нет...

Автор: Aleksandor 17.11.2006, 22:30
Во втором случае не используется hdcMem и bitmap, наверное стоит копать в ту сторону smile  
если битмапы создаются каждый раз заново, то их надо удалять, из текста не видно откуда они берутся. у меня вот такой код - работает нормально. ТТТ
Код

hdcMem = CreateCompatibleDC(lpdis->hDC); 
hbmOld = (HBITMAP) SelectObject(hdcMem, hbm[i]); 
BitBlt(lpdis->hDC,  lpdis->rcItem.left, y, 16, 16, hdcMem, 0, 0, SRCCOPY); 

SelectObject(hdcMem, hbmOld);
DeleteDC(hdcMem); 

Автор: leopard678 17.11.2006, 22:35
bitmap создаются при содзпнии класса из рессурсов..
hbmOld не помогает  smile 

Автор: Aleksandor 17.11.2006, 22:44
А если без класса попробовать? Хорошо бы BoundsChecker еще задействовать для отладки. Или на худой конец полностью код в студию  smile 

Автор: leopard678 20.11.2006, 08:17
главное окно:
Код

case WM_PAINT:
            {
                hdc = BeginPaint(hWnd, &ps);        
                    paint(hdc);
                EndPaint(hWnd, &ps);                
                
                break;
            }


Код

CSimpleButton sbOptions;
.............
sbOptions.SetBMP(hInst,IDB_BOPTIONS_NORMAL,IDB_BOPTIONS_HIGHLIGHT,IDB_BOPTIONS_HIGHLIGHT,IDB_BOPTIONS_DISABLE);
        sbOptions.SetPosition(30,325);
        sbOptions.SetSize(225,44);
        sbOptions.SetState(BT_NORMAL);
.............
void paint(HDC hdc)
{    
                fon=LoadBitmap(hInst,MAKEINTRESOURCE(IDB_FON));
                
                d=CreateCompatibleDC(hdc);
                PatBlt(d,0,0,640,480,WHITENESS);
                SelectObject(d,fon);

                sbOptions.Draw(d);

                BitBlt(hdc,0,0,640,480,d,0,0,SRCCOPY);
                DeleteDC(d);
                
          
}


класс кнопки
Код

//---Установка Изображений(из ресурсов) на кнопке----------------------------//
void CSimpleButton::SetBMP(HINSTANCE a_hinstance_app, WORD a_strBMP_Normal, WORD a_strBMP_HighLight, WORD a_strBMP_Push, WORD m_strBMP_Disable)
{
     m_hbBMP_Normal=LoadBitmap(a_hinstance_app,MAKEINTRESOURCE(a_strBMP_Normal));
     m_hbBMP_HighLight=LoadBitmap(a_hinstance_app,MAKEINTRESOURCE(a_strBMP_HighLight));
     m_hbBMP_Push=LoadBitmap(a_hinstance_app,MAKEINTRESOURCE(a_strBMP_Push));
     m_hbBMP_Disable=LoadBitmap(a_hinstance_app,MAKEINTRESOURCE(m_strBMP_Disable));
     
}


Код

void CSimpleButton::Draw(HDC pDC)
{
    dcMem1 = CreateCompatibleDC(pDC);
    HBITMAP hOldbm;

    //--выбор изображения кнопки
    switch(m_iState) 
    {
        case 0:
            {
                // Выбираем изображение bitmap в контекст памяти
                 hOldbm = (HBITMAP)SelectObject(dcMem1,m_hbBMP_Disable);
                break;
            }
        case 1:
            {
                // Выбираем изображение bitmap в контекст памяти
                 hOldbm = (HBITMAP)SelectObject(dcMem1,m_hbBMP_Normal);
                break;
            }
        case 2:
            {
                // Выбираем изображение bitmap в контекст памяти
                 hOldbm = (HBITMAP)SelectObject(dcMem1,m_hbBMP_HighLight);
                break;
            }
        case 3:
            {
                // Выбираем изображение bitmap в контекст памяти
                 hOldbm = (HBITMAP)SelectObject(dcMem1,m_hbBMP_Push);
                break;
            }        
        default:   // если значение состояния вне допустимого - ничего не рисуем
            {

                break;
            }        
    }

    if (hOldbm)
    {
        BitBlt(pDC,m_iX,m_iY,m_iCX,m_iCY,dcMem1,0,0,SRCCOPY);

        // Восстанавливаем контекст памяти
        SelectObject(dcMem1, hOldbm);
    }


        ::DeleteDC(dcMem1);
        
}

Автор: leopard678 20.11.2006, 08:48
Похоже проблема была в
Код

void paint(HDC hdc)
{    
                fon=LoadBitmap(hInst,MAKEINTRESOURCE(IDB_FON));


только не понятно почему при выводе не через BitBlt ,а через GetPixel, SetPixel всё работало нормально....

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