Прозрачный фон окна - Assembler

Узнай цену своей работы

Формулировка задачи:

Приветствую! Создал окно с прозрачным фоном (WS_EX_LAYERED +WS_POPUP+ SetLayeredWindowAttributes,eax,0,200,LWA_ALPHA) и все получилось, но вот проблема: при навешивании кнопок, едитов и т.п. они наследуют прозрачность. Как убрать наследственность ?

Решение задачи: «Прозрачный фон окна»

textual
Листинг программы
format PE GUI 4.0
entry start
 
include 'win32a.inc'
include 'macro\if.inc'
 
HTCAPTION = 2
section '.data' data readable writeable
_class db 'WIN1',0
_title db 'Основное Окно',0
_error db 'Ошибка основного окна',0
_cstatic db 'STATIC',0
_tmin db 'MIN:',0 
_classb db 'BUTTON',0
_textb db 'КНОПКА',0
 
hBitmap dd ?            ;дескриптор фонового изображения 
hdc dd ?                ;дескриптор  холста
hMemDC dd ?             ;дескриптор  копии холста
my dd ?
 
wc WNDCLASS 0,WindowProc,0,0,0,0,0,COLOR_BTNFACE+1,0,_class
msg MSG
ps PAINTSTRUCT
rect RECT
 
;:
section '.code' code readable executable
start:
 
invoke GetModuleHandle,0
mov [wc.hInstance],eax
invoke LoadIcon,0,IDI_APPLICATION
mov [wc.hIcon],eax
invoke LoadCursor,0,IDC_ARROW
mov [wc.hCursor],eax
invoke RegisterClass,wc
cmp eax,0
je error
 
invoke CreateWindowEx,WS_EX_LAYERED,_class,_title,WS_VISIBLE+WS_POPUP+WS_BORDER\
,128,128,900,700,0,0,[wc.hInstance],0
cmp eax,0
je error
mov [wc.hIcon],eax
invoke SetLayeredWindowAttributes,eax,0,200,LWA_ALPHA
mtk_msg_loop:
invoke GetMessage,msg,0,0,0
cmp eax,0
je mtk_end_loop
invoke TranslateMessage,msg
invoke DispatchMessage,msg
jmp mtk_msg_loop
 
error:
invoke MessageBox,0,_error,0,MB_ICONERROR+MB_OK
 
mtk_end_loop:
invoke ExitProcess,[msg.wParam]
 
 
 
proc WindowProc hwnd,wmsg,wparam,lparam
push ebx esi edi
cmp [wmsg],WM_CREATE
je .wmcreate
cmp [wmsg],WM_LBUTTONDOWN
je .wmlbuttondown
cmp [wmsg],WM_DESTROY
je .wmdestroy
cmp [wmsg],WM_PAINT
je .wmpaint
.defwndproc: ;::
invoke DefWindowProc,[hwnd],[wmsg],[wparam],[lparam]
jmp .finish
;:
.wmcreate: ;::
 
invoke CreateWindowEx,0,_cstatic,_tmin,WS_VISIBLE+WS_CHILD, 60,120,40,20,[hwnd],0,[wc.hInstance],NULL
invoke CreateWindowEx,0,_classb,_textb,WS_VISIBLE+WS_CHILD+BS_PUSHBUTTON, 60,60,100,50,[hwnd],1001,[wc.hInstance],NULL
invoke SetLayeredWindowAttributes,eax,0,0,LWA_ALPHA
invoke LoadBitmap,[wc.hInstance],1
mov [hBitmap],eax
invoke GetWindowDC,[hwnd]
mov [hdc],eax
invoke CreateCompatibleDC,[hdc]
mov [hMemDC],eax
invoke SelectObject,[hMemDC],[hBitmap]
; вызов процедуры создания региона
invoke GetClientRect,[hwnd],rect
push [rect.bottom]
push [rect.right]
push [hMemDC]
call MakeRegion
; применить регион к окну
invoke SetWindowRgn,[hwnd],eax,TRUE
invoke ReleaseDC,[hwnd],[hdc]
invoke DeleteDC,[hMemDC]
jmp .finish
;:
 
.wmpaint: ;::
invoke BeginPaint,[hwnd],ps
mov [hdc],eax
invoke CreateCompatibleDC,[hdc]
mov [hMemDC],eax
invoke SelectObject,[hMemDC],[hBitmap]
invoke GetClientRect,[hwnd],rect
invoke BitBlt,[hdc],0,0,[rect.right],[rect.bottom],[hMemDC],0,0,SRCCOPY
invoke DeleteDC,[hMemDC]
invoke EndPaint,[hwnd],ps
jmp .finish
;:
 
 
.wmlbuttondown: ;::
invoke ReleaseCapture
invoke SendMessage,[hwnd],WM_NCLBUTTONDOWN,HTCAPTION,0
jmp .finish
;:
.wmdestroy: ;::
invoke PostQuitMessage,0
mov eax,0
;:
.finish: ;::
pop edi esi ebx
ret
;:
endp
proc MakeRegion var_hDC,var_PicWidth,var_PicHeight
 
local var_X:DWORD ; столбец
local var_Y:DWORD ; ряд
local var_StartLineX:DWORD ; левый край текущего региона
local var_FullRegion:DWORD ; комплексный регион
local var_LineRegion:DWORD ; текущий регион
local var_TransparantColor:DWORD ; прозрачный цвет (исключается из региона)
local var_InFirstRegion:DWORD ; первый регион (Да/Нет)
local var_Inline:DWORD ; создается линия региона (Да/Нет)
 
mov [var_InFirstRegion],TRUE
mov [var_Inline],FALSE
mov [var_X],0
mov [var_Y],0
mov [var_StartLineX],0
 
invoke GetPixel,[var_hDC],0,0 ; получаем прозрачный цвет из левого верхнего пикселя картинки
mov [var_TransparantColor],eax
 
mov ebx, [var_PicHeight]
.while [var_Y] < ebx ; повторяем до нижнего ряда
mov ebx,[var_PicWidth]
 
.while [var_X] <= ebx ; повторяем до правого столбца в каждом ряду
 
invoke GetPixel,[var_hDC],[var_X],[var_Y] ; получаем текущий пиксель
mov ebx,[var_PicWidth]
 
; проверяем, является ли пиксель прозрачным или достигнут конец ряда
.if eax=[var_TransparantColor] | [var_X]=ebx
 
; если это так, то проверим еще, имеется ли у нас линия, которую надо добавить в регион
; или это лишь очередной прозрачный пиксель, и мы должны просто двигаться дальше
 
.if [var_Inline]=TRUE
mov [var_Inline],FALSE
mov ebx,[var_Y]
inc ebx
invoke CreateRectRgn,[var_StartLineX],[var_Y],[var_X],ebx
mov [var_LineRegion],eax
.if [var_InFirstRegion]=TRUE
; если это первый созданный регион, то мы просто
; сохраним его дескриптор в комплексный регион
push [var_LineRegion]
pop [var_FullRegion]
mov [var_InFirstRegion],FALSE
.else
; иначе — добавим полученный регион к комплексному региону
; а затем удалим текущий для освобождения памяти
 
invoke CombineRgn,[var_FullRegion],[var_FullRegion],[var_LineRegion],RGN_OR
invoke DeleteObject,[var_LineRegion]
.endif
.endif
.else
.if [var_Inline]=FALSE
; текущий пиксель не прозрачный, это не конец ряда, и мы не на этапе создания линии
; значит, этот пиксель будем считать первым пикселем очередной линии
mov [var_Inline],TRUE
push [var_X]
pop [var_StartLineX]
.endif
.endif
inc [var_X]
mov ebx,[var_PicWidth]
.endw
inc [var_Y]
mov [var_X],0
mov ebx,[var_PicHeight]
.endw
 
mov eax,[var_FullRegion] ; возвращаем готовый регион в точку вызова процедуры
 
ret
 
endp
 
;:
section '.idata' import data readable writeable
 
 
library gdi32,'GDI32.DLL',\
kernel32,'KERNEL32.DLL',\
user32,'USER32.DLL'
 
include 'api\gdi32.inc'
include 'api\kernel32.inc'
include 'api\user32.inc'
;:
section '.rsrc' resource data readable
 
directory RT_BITMAP,bitmaps;,RT_DIALOG,dialogs,RT_ICON,icons,RT_GROUP_ICON,group_icons,RT_VERSION,versions
 
;resource icons,1,LANG_NEUTRAL,icon_data
;resource group_icons,17,LANG_NEUTRAL,main_icon
resource bitmaps,1,LANG_NEUTRAL,pict
;resource versions,2,LANG_ENGLISH+SUBLANG_DEFAULT,version
;resource dialogs,37,LANG_ENGLISH+SUBLANG_DEFAULT,main
 
bitmap pict,'fon.bmp'
;icon main_icon,icon_data,'bmp.ico'
 
;dialog main,'Картинка в диалоге',10,10,213,147,WS_VISIBLE+WS_POPUP+\
;WS_CAPTION+WS_SYSMENU+DS_CENTER+DS_MODALFRAME
;dialogitem 'STATIC',IDR_PICT,-1,0,0,0,0,WS_VISIBLE+SS_BITMAP
;dialogitem 'BUTTON','&OK',IDOK,50,130,45,15,WS_VISIBLE+WS_TABSTOP+BS_PUSHBUTTON
;dialogitem 'BUTTON','&Cancel',IDCANCEL,120,130,45,15,WS_VISIBLE+WS_TABSTOP+BS_PUSHBUTTON
;enddialog
 
 
;versioninfo version,VOS__WINDOWS32,VFT_APP,VFT2_UNKNOWN,LANG_ENGLISH+SUBLANG_DEFAULT,0,\
;'FileDescription','Bitmap example',\
;'LegalCopyright',<'Copyright ',0A9h,' BarMentaLisk 2008'>,\
;'FileVersion','0.1',\
;'ProductVersion','0.1',\
;'OriginalFilename','bmp_example'
;:

Оцени полезность:

7   голосов , оценка 3.857 из 5