Go Back   Armenian Knowledge Base > Technical sections > Languages, Compilers, Interpreters

Reply
 
Thread Tools

Полупрозрачные изображения в MFC
Old 20.08.2002, 03:22   #1
Главный инспектор снов
 
Dream_InspectoR's Avatar
 
Join Date: 01 2002
Location: Yerevan, Armenia
Posts: 329
Rep Power: 0
Post Полупрозрачные изображения в MFC

Вопрос такой. У меня есть изображение (bitmap в ресурсах) я хочу поствить его на форму, однако само изображение не прямоугольное, а фон мне не нужен. как сделать так, чтоб фон был прозрачным. Например с курсорами всегда так, часть прорисовывается а часть нет, хотя они тоже квадратные изображения.
__________________
Kill'em!!! Kill'em all!!!

Old 20.08.2002, 13:01   #2
Академик
 
greka's Avatar
 
Join Date: 09 2001
Location: inside myself
Posts: 5,369
Rep Power: 6
Post

нет инфы под рукою, поищи на сайтах...

http://www.codeguru.com, http://www.codeproject.com, etc.
__________________
И повешенные могут качаться в неположенную сторону. /С.Е.Лец/

Old 03.10.2002, 18:33   #3
Младенец
 
Join Date: 10 2002
Location: Chicago NW Suburbs, IL, US
Posts: 14
Rep Power: 0
Post

sozdat' region nuzhnoy formy, potom
SetWindowRgn() - eto esli pro otdelnoe okno..

a esli pro prosto bitmap - to nado delat' masked bitmap, t.e. risovat' v 2 proxoda.

1. s pomoshyu SRCAND risuem masku
2. s pomoshyu SCRCOPY risuem image

Best source of knowledge is MSDN !
__________________
The best way to predict the future is to create it

Old 06.10.2002, 01:46   #4
Дошкольник
 
Join Date: 03 2002
Location: Yerevan
Posts: 111
Rep Power: 0
Post

А вообще функция есть в 2000 - TransparentBlt - можно с ее помощью можно создать битмап с прозрачным фоном быстро и без шума.

Есть еще один не совсем простой способ, но зато удобный иногда. Надо считать битмап как бинарный ресурс, формат DIB-а - известен, поменять в таблице цветов соответствующий цвет. А потом из этих, измененных в нашу пользу, данных создать пригодный для использования битмап.

Код примерно такой:

Сначала загружаем ресурс как бинарный:

Code:
HGLOBAL handle = ::LoadResource(AfxGetInstanceHandle(), FindResource(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_LOGO), RT_BITMAP));
Потом получаем указатель на эти бинарные данные.

Code:
BITMAPINFO* bitmapInfo = (BITMAPINFO*)(::LockResource(handle));
BITMAPINFOHEADER* bitmapHeader = &bitmapInfo->bmiHeader;
Считаем количество используемых цветов в битмапе согласно его формату:

Code:
    
int colorCount = 1 << bitmapHeader->biBitCount;
int size = sizeof(BITMAPINFOHEADER) + colorCount * sizeof(RGBQUAD);
Копируeм заголовок битмапа в укромное место:

Code:
BITMAPINFO* bitmapInfoCopy = (BITMAPINFO*)(new BYTE [size]);
memcpy(bitmapInfoCopy, bitmapInfo, size);
Извлекаем таблицу цветов из заголовка:

Code:
DWORD* colorTable = (DWORD*)(bitmapInfoCopy->bmiColors);
Заменяем белый цвет (255, 255, 255) предполагаемого фона из битмапа на серый BTN_FACE - цвет формы, в частности у меня там в диалоге лого рисовалось.

Code:
#define RGB_TO_RGBQUAD(r,g,b)   (RGB(b,g,r))
#define CLR_TO_RGBQUAD(clr)     (RGB(GetBValue(clr), GetGValue(clr), GetRValue(clr)))

DWORD bkColor = CLR_TO_RGBQUAD(GetSysColor(COLOR_BTNFACE));
for (int i = 0; i < colorCount; i++)
   if (colorTable[i] == RGB_TO_RGBQUAD(255, 255, 255))
         colorTable[i] = bkColor;
Извлекаем указатель на пиксельные данные битмапа - находящиеся прямо за заголовком.

Code:
BYTE* bitmapData = (BYTE*)(bitmapHeader + 1);
bitmapData += colorCount * sizeof(RGBQUAD);
Создаем реальный битмап, подставив ему новый заголовок с "правильными" цветами в таблице.

Code:
CClientDC screenDC(NULL);
СBitmap logo;
logo.Attach(CreateDIBitmap(screenDC.m_hDC, bitmapHeader, CBM_INIT, bitmapData, bitmapInfoCopy, DIB_RGB_COLORS));
Ну и наконец удаляем копию заголовка:

Code:
delete [] (BYTE*)bitmapInfoCopy;
Копия заголовка нужна, потому что данные полученные по указателю на ресурс нельзя изменить - они readonly - по крайней мере в NT и 2000.

Ну и напоследок, 100% гарантии не даю, но для простеньких битмапов у меня работало. Может не работать на нестандартных битмапах использующих различные расширения - предусмотренные форматом. Умышленных багов в коде, как это положено традицией - нет, это все таки не журнал

По-крайней мере это проще, чем вручную создавать маску и конструровать битмап, если нужно чтобы работало под 95/98/NT.

Old 06.10.2002, 16:07   #5
Младенец
 
Join Date: 10 2002
Location: Chicago NW Suburbs, IL, US
Posts: 14
Rep Power: 0
Post

Nu esli rech idet o tom chto by narisovat' bitmap odnotoonom izvestnom fone, to vse proshe.

::CreateMappedBitmap(), zadavaya COLORMAP s transofrmom izvestogo cveta (RGB(192.192.192)naprimer) na cvet fona..

No esli rech idet o TRUE tranparent, to nuzhno masku delat'..
__________________
The best way to predict the future is to create it

Old 07.10.2002, 02:29   #6
Дошкольник
 
Join Date: 03 2002
Location: Yerevan
Posts: 111
Rep Power: 0
Post

Судя по вопросу маска не нужна. Так что использование CreateMappedBitmap(), думаю, будет правильнее всего - а код приведенный мною всего лишь его ручная и ограниченная реализация.

Old 09.10.2002, 01:33   #7
Главный инспектор снов
 
Dream_InspectoR's Avatar
 
Join Date: 01 2002
Location: Yerevan, Armenia
Posts: 329
Rep Power: 0
Post

Да спокойно народ я уже давно с этим разобрался. функции TransparentBlt или AlphaBlend в msimg32.dll это делают
__________________
Kill'em!!! Kill'em all!!!

Old 09.10.2002, 02:24   #8
Moderator
 
acid's Avatar
 
Join Date: 09 2001
Location: South Korea, Gumi
Posts: 7,699
Blog Entries: 16
Rep Power: 7
Post

Quote:
Originally posted by Dream_InspectoR:
Да спокойно народ я уже давно с этим разобрался. функции TransparentBlt или AlphaBlend в msimg32.dll это делают
С приездом дорогой

Old 09.10.2002, 19:55   #9
Дошкольник
 
Join Date: 03 2002
Location: Yerevan
Posts: 111
Rep Power: 0
Post

Ну и молодец !
Какая молодежь умная растет !
Reply




Реклама:
реклама
Buy text link .

All times are GMT. The time now is 03:23.
Top

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.