REAL ImageButton control!
BlitzPlus Forums/BlitzPlus Programming/REAL ImageButton control!
| ||
One simple command: SetButtonImage(button,image) ![]() I chose this so that you can change the button image at any time. The function accepts a regular old Blitz image. Use SetButtonImage(button,0) to change the ImageButton back into a regular button. win=CreateWindow("ImageButton",200,200,400,300,0,3) i=LoadImage("blitzlogo.bmp") w=ImageWidth(i) h=ImageHeight(i) button=CreateButton("",(ClientWidth(win)-w)/2,(ClientHeight(win)-h)/2,w,h,win) SetButtonImage button,i Repeat Until WaitEvent()=$803 Const BM_SETIMAGE=247 Const IMAGE_BITMAP=0 Const IMAGE_ICON=1 Const BS_BITMAP=128 Const GWL_STYLE=-16 Const LR_DEFAULTSIZE=64 Const LR_LOADFROMFILE=16 Const LR_SHARED=32768 Function SetButtonImage(button,image) hbutton=QueryObject(button,1) flags=GetWindowLong(hbutton,GWL_STYLE) If image If Not (BS_BITMAP And flags) SetWindowLong hbutton,GWL_STYLE,flags+BS_BITMAP Else If (BS_BITMAP And flags) SetWindowLong hbutton,GWL_STYLE,flags-BS_BITMAP Return EndIf w=ImageWidth(image) h=ImageHeight(image) ibuffer=ImageBuffer(image) LockBuffer ibuffer pixels=CreateBank(w*h*4) For y=0 To h-1 For x=0 To w-1 PokeInt pixels,4*(y*w+x)+0,ReadPixelFast(x,y,ibuffer) Next Next UnlockBuffer ibuffer i=CreateBitmap(w,h,1,32,pixels) FreeBank pixels If Not i Return oldimage=SendMessage(hbutton,BM_SETIMAGE,IMAGE_BITMAP,i) If oldimage DeleteObject(oldimage) Return True End Function |
| ||
CreateBitMap() function not found. |
| ||
Function 'getwindowlong' not found |
| ||
And I expect that SetWindowLong, SendMessage and DeleteObject will also not be found. Could you provide decls and supporting library references? |
| ||
Those are all API functions, which you should already have installed. Get the gdi32, kernel32, and user32 decls files from the code archive. |
| ||
Cool, this works great! You should post it in the code archives (and mention that it needs those userlibs)! |
| ||
snagged kernal32.decls, user32.decls, and gdi32.decls. All stashed with my other .decl files. SetWindowLong, SendMessage, DeleteObject, GetWindowLong, and CreateBitmap still not found. Eyeballed the .decl files and see they all have api_ prefixes. Edited the above source into: api_SetWindowLong, api_SendMessage, api_DeleteObject, api_GetWindowLong, and api_CreateBitmap. It now passes the syntax check and runs before crashing. It abends at the following line: oldimage=api_SendMessage(hbutton,BM_SETIMAGE,IMAGE_BITMAP,i) The abend is your classic 0xc0000005 I did mod the source of the image to point to the ide_toolbar.bmp in the BlitzPlus\cfg subdirectory. What am I missing? |
| ||
The user32.decls needs a tweak. Per aero: Use this: SendMessage%(hwnd%,wMsg%,wParam%,lParam%) : "SendMessageA" NOT this: SendMessage%(hwnd%,wMsg%,wParam%,lParam*) : "SendMessageA" |
| ||
crashes here too |
| ||
Use this: SendMessage%(hwnd%,wMsg%,wParam%,lParam%) : "SendMessageA" NOT this: SendMessage%(hwnd%,wMsg%,wParam%,lParam*) : "SendMessageA" |
| ||
yup changed it but still crashes |
| ||
Did all the above but the only thing i get is a blank button with width and height of the image loaded... (Tried bmp and jpg filetypes...) Any suggestions or advice? |
| ||
OK. Create a userlib file if you don't already have one..lib "user32.dll" USER32_SendMessage%(hWnd%,Msg%,wParam%,lParam%):"SendMessageA" USER32_GetWindowLong%(hWnd%,nIndex%):"GetWindowLongA" USER32_SetWindowLong%(hWnd%,nIndex%,dwNewLong%):"SetWindowLongA" .lib "gdi32.dll" GDI32_CreateBitmap%(nWidth%,nHeight%,nPlanes%,nBitCount%,lpBits*):"CreateBitmap" GDI32_DeleteObject%(hObject%):"DeleteObject" Change the code to this: win=CreateWindow("ImageButton",200,200,400,300,0,3) i=LoadImage("blitzlogo.bmp") w=ImageWidth(i) h=ImageHeight(i) button=CreateButton("",(ClientWidth(win)-w)/2,(ClientHeight(win)-h)/2,w,h,win) SetButtonImage button,i Repeat Until WaitEvent()=$803 Const BM_SETIMAGE=247 Const IMAGE_BITMAP=0 Const IMAGE_ICON=1 Const BS_BITMAP=128 Const GWL_STYLE=-16 Const LR_DEFAULTSIZE=64 Const LR_LOADFROMFILE=16 Const LR_SHARED=32768 Function SetButtonImage(button,image) hbutton=QueryObject(button,1) flags=USER32_GetWindowLong(hbutton,GWL_STYLE) If image If Not (BS_BITMAP And flags) USER32_SetWindowLong hbutton,GWL_STYLE,flags+BS_BITMAP Else If (BS_BITMAP And flags) USER32_SetWindowLong hbutton,GWL_STYLE,flags-BS_BITMAP Return EndIf w=ImageWidth(image) h=ImageHeight(image) ibuffer=ImageBuffer(image) LockBuffer ibuffer pixels=CreateBank(w*h*4) For y=0 To h-1 For x=0 To w-1 PokeInt pixels,4*(y*w+x)+0,ReadPixelFast(x,y,ibuffer) Next Next UnlockBuffer ibuffer i=GDI32_CreateBitmap(w,h,1,32,pixels) FreeBank pixels If Not i Return oldimage=USER32_SendMessage(hbutton,BM_SETIMAGE,IMAGE_BITMAP,i) If oldimage GDI32_DeleteObject(oldimage) Return True End Function Find an image or whatever and put it in the same directory as the file (if it's saved then that directory, if not then its in program files\blitzplus\tmp\). Change the above "LoadImage" part to the name of the image file. |
| ||
I like the code.. Thanks! I hope you don't mind but I made an adjustment to it. Give this a try also:win=CreateWindow("ImageButton",200,200,400,300,0,3) i=LoadImage("test2.bmp"); These two images should be the same size but look different j=LoadImage("test1.bmp"); (other image) w=ImageWidth(i) h=ImageHeight(i) button=CreateButton("",(ClientWidth(win)-w)/2,(ClientHeight(win)-h)/2,w,h,win) SetButtonImage button,i current = i Repeat ID = WaitEvent(1) Select ID Case $401 Select EventSource() Case button If current = j Then current = i Else current = j SetButtonImage button,current End Select Case $803 End End Select Forever Const BM_SETIMAGE=247 Const IMAGE_BITMAP=0 Const IMAGE_ICON=1 Const BS_BITMAP=128 Const GWL_STYLE=-16 Const LR_DEFAULTSIZE=64 Const LR_LOADFROMFILE=16 Const LR_SHARED=32768 Function SetButtonImage(button,NEWimage) hbutton=QueryObject(button,1) flags=GetWindowLong(hbutton,GWL_STYLE) If (Not image = NEWimage) If Not (BS_BITMAP And flags) SetWindowLong hbutton,GWL_STYLE,flags+BS_BITMAP Else If (BS_BITMAP And flags) SetWindowLong hbutton,GWL_STYLE,flags-BS_BITMAP Return EndIf w=ImageWidth(NEWimage) h=ImageHeight(NEWimage) ibuffer=ImageBuffer(NEWimage) LockBuffer ibuffer pixels=CreateBank(w*h*4) For y=0 To h-1 For x=0 To w-1 PokeInt pixels,4*(y*w+x)+0,ReadPixelFast(x,y,ibuffer) Next Next UnlockBuffer ibuffer tmp=CreateBitmap(w,h,1,32,pixels) FreeBank pixels If Not tmp Return oldimage=SendMessage(hbutton,BM_SETIMAGE,IMAGE_BITMAP,tmp) If oldimage DeleteObject(oldimage) image = NEWimage Return True End Function |
| ||
Is there any way to use transparent images on the buttons? I tried white, pink and black as transparent color but nothing works. Any ideas? |