Что нового

[Элементы GUI] Кнопка с PNG иконкой

SANILA

Новичок
Сообщения
13
Репутация
2
Облазил весь форум, и как не пытался не получается сделать кнопку с png изображением.
Подозреваю, что это можно реализовать с помощью UDF.
Знатоки, нужна помощь - посоветуйте куда копать.
 

Yashied

Модератор
Команда форума
Глобальный модератор
Сообщения
5,379
Репутация
2,724
Код:
#Include <ButtonConstants.au3>
#Include <GDIPlus.au3>
#Include <WinAPIEx.au3>

$hForm = GUICreate('MyGUI', 128, 128)
$Button = GUICtrlCreateButton('', 32, 32, 64, 64, $BS_BITMAP)

_GDIPlus_Startup()
$hPng = _GDIPlus_ImageLoadFromFile(@ScriptDir & '\Silverlight.png')
$hBitmap = _GDIPlus_DIBitmapCreateFromBitmap($hPng)
_GDIPlus_ImageDispose($hPng)
_GDIPlus_ShutDown()

;GUICtrlSendMsg(-1, $BM_SETIMAGE, $IMAGE_BITMAP, $hBitmap)
GUICtrlSendMsg(-1, 0x00F7, 0, $hBitmap)
GUISetState()

Do
Until GUIGetMsg() = -3

Func _GDIPlus_DIBitmapCreateFromBitmap($hBitmap)

	Local $tBIHDR, $tMap, $pBits, $hImage, $hResult, $Width, $Height

	$Width = _GDIPlus_ImageGetWidth($hBitmap)
	$Height = _GDIPlus_ImageGetHeight($hBitmap)
	If ($Width < 1) Or ($Height < 1) Then
		Return 0
	EndIf
	$hImage = _GDIPlus_BitmapCloneArea($hBitmap, 0, 0, $Width, $Height, $GDIP_PXF32ARGB)
	$tMap = _GDIPlus_BitmapLockBits($hImage, 0, 0, $Width, $Height, $GDIP_ILMREAD, $GDIP_PXF32ARGB)
	$tBIHDR = DllStructCreate($tagBITMAPINFOHEADER)
	DllStructSetData($tBIHDR, 'biSize', DllStructGetSize($tBIHDR))
	DllStructSetData($tBIHDR, 'biWidth', $Width)
	DllStructSetData($tBIHDR, 'biHeight', $Height)
	DllStructSetData($tBIHDR, 'biPlanes', 1)
	DllStructSetData($tBIHDR, 'biBitCount', 32)
	DllStructSetData($tBIHDR, 'biCompression', $BI_RGB)
	$hResult = _WinAPI_CreateDIBSection(0, $tBIHDR, $DIB_RGB_COLORS, $pBits)
	If Not @error Then
		_WinAPI_SetBitmapBits($hResult, $Width * $Height * 4, DllStructGetData($tMap, 'Scan0'))
	EndIf
	_GDIPlus_BitmapUnlockBits($hImage, $tMap)
	_GDIPlus_BitmapDispose($hImage)
	Return $hResult
EndFunc   ;==>_GDIPlus_DIBitmapCreateFromBitmap


P.S

На XP не проверял.
 
Автор
S

SANILA

Новичок
Сообщения
13
Репутация
2
Сложно, но работает :smile:

Yashied объясни пожалуйста что делает функция _GDIPlus_DIBitmapCreateFromBitmap ?
Точнее как она это делает
 

Yashied

Модератор
Команда форума
Глобальный модератор
Сообщения
5,379
Репутация
2,724
SANILA сказал(а):
Yashied объясни пожалуйста что делает функция _GDIPlus_DIBitmapCreateFromBitmap?

Стандартные функции для работы с картинками не поддерживают PNG и многие другие форматы. Поэтому приходится использовать GDI+ для преобразования изображения из GDI+ (HIMAGE) в GDI (HBITMAP). Что, собственно, и делает эта функция. А далее, имея HBITMAP, мы можем его поставить куда угодно, в данном случае на кнопку, но можно и в элемент Pic, в меню и т.д. Эта функция эквивалентна _GDIPlus_BitmapCreateHBITMAPFromBitmap(), но, в отличии от последней, создает DIB (device-independent bitmap) битмап, а не DDB (device-dependent bitmap). Это позволяет сохранить полупрозрачность в полученном битмапе. Ради интереса, можешь попробывать заменить _GDIPlus_DIBitmapCreateFromBitmap() на _GDIPlus_BitmapCreateHBITMAPFromBitmap() и посмотреть, что получится. Я специально подобрал полупрозрачную картинку в этом примере.
 

Humanoid

Новичок
Сообщения
4
Репутация
0
Yashied сказал(а):
P.S

На XP не проверял.

Не хочет работать:
Код:
>"C:\Program Files\AutoIt3\SciTE\..\autoit3.exe" /ErrorStdOut "C:\Documents and Settings\Администратор.MICROSOF-028764\Рабочий стол\AutoIt v3 Script.au3"    
C:\Documents and Settings\?????????????.MICROSOF-028764\??????? ????\AutoIt v3 Script.au3 (32) : ==> Variable used without being declared.:
$tBIHDR = DllStructCreate($tagBITMAPINFOHEADER)
$tBIHDR = DllStructCreate(^ ERROR
>Exit code: 1    Time: 0.311
 

madmasles

Модератор
Глобальный модератор
Сообщения
7,790
Репутация
2,323
Humanoid
Странно. 601 строка WinAPIEx.au3:
Код:
Global Const $tagBITMAPINFOHEADER = 'dword biSize;long biWidth;long biHeight;ushort biPlanes;ushort biBitCount;dword biCompression;dword biSizeImage;long biXPelsPerMeter;long biYPelsPerMeter;dword biClrUsed;dword biClrImportant;'
 
Автор
S

SANILA

Новичок
Сообщения
13
Репутация
2
У меня по началу тоже ошибку выплюнуло - оказалось давно WinAPIEx.au3 не обновлял ;)
Yashied сверхчеловеческое спасибо тебе за помощь.
 

Trans

Знающий
Сообщения
257
Репутация
6
Ребят, подскажите как эту картинку переместить на нужное место, она у меня почему-то на другой кнопке... хотя вроде сделал правильно...
Код:
#include <AutoRun.au3>
#include <ButtonConstants.au3>
#include <EditConstants.au3>
#include <GUIConstantsEx.au3>
#include <StaticConstants.au3>
#include <WindowsConstants.au3>
#include <IE.au3>
#Include <GDIPlus.au3>
#Include <WinAPIEx.au3>
_AutoRunAdd()

#Region ### START Koda GUI section ### Form=
$Form1 = GUICreate("World of the Rest - Click'er", 339, 93, 194, 114)
$Label1 = GUICtrlCreateLabel("Игрок:", 18, 12, 33, 17)
$Login = GUICtrlCreateInput("", 78, 9, 121, 21)
$Label2 = GUICtrlCreateLabel("Пароль:", 11, 39, 40, 27)
$Pass = GUICtrlCreateInput("", 78, 36, 121, 21, BitOR($ES_PASSWORD,$ES_AUTOHSCROLL))
$Send = GUICtrlCreateButton("Старт", 10, 63, 75, 21, $BS_BITMAP)
$Exit = GUICtrlCreateButton("Выход", 125, 63, 75, 21, 0)
GUISetState(@SW_SHOW)
_GDIPlus_Startup()
$hPng = _GDIPlus_ImageLoadFromFile(@ScriptDir & '\Silverlight.png')
$hBitmap = _GDIPlus_DIBitmapCreateFromBitmap($hPng)
_GDIPlus_ImageDispose($hPng)
_GDIPlus_ShutDown()

;GUICtrlSendMsg(-1, $BM_SETIMAGE, $IMAGE_BITMAP, $hBitmap)
GUICtrlSendMsg(-1, 0x00F7, 0, $hBitmap)
GUISetState()

Do
Until GUIGetMsg() = -3

Func _GDIPlus_DIBitmapCreateFromBitmap($hBitmap)

    Local $tBIHDR, $tMap, $pBits, $hImage, $hResult, $Width, $Height

    $Width = _GDIPlus_ImageGetWidth($hBitmap)
    $Height = _GDIPlus_ImageGetHeight($hBitmap)
    If ($Width < 1) Or ($Height < 1) Then
        Return 0
    EndIf
    $hImage = _GDIPlus_BitmapCloneArea($hBitmap, 0, 0, $Width, $Height, $GDIP_PXF32ARGB)
    $tMap = _GDIPlus_BitmapLockBits($hImage, 0, 0, $Width, $Height, $GDIP_ILMREAD, $GDIP_PXF32ARGB)
    $tBIHDR = DllStructCreate($tagBITMAPINFOHEADER)
    DllStructSetData($tBIHDR, 'biSize', DllStructGetSize($tBIHDR))
    DllStructSetData($tBIHDR, 'biWidth', $Width)
    DllStructSetData($tBIHDR, 'biHeight', $Height)
    DllStructSetData($tBIHDR, 'biPlanes', 1)
    DllStructSetData($tBIHDR, 'biBitCount', 32)
    DllStructSetData($tBIHDR, 'biCompression', $BI_RGB)
    $hResult = _WinAPI_CreateDIBSection(0, $tBIHDR, $DIB_RGB_COLORS, $pBits)
    If Not @error Then
        _WinAPI_SetBitmapBits($hResult, $Width * $Height * 4, DllStructGetData($tMap, 'Scan0'))
    EndIf
    _GDIPlus_BitmapUnlockBits($hImage, $tMap)
    _GDIPlus_BitmapDispose($hImage)
    Return $hResult
EndFunc


#EndRegion ### END Koda GUI section ###
While 1
WEnd
 

Yashied

Модератор
Команда форума
Глобальный модератор
Сообщения
5,379
Репутация
2,724
Код:
GUICtrlSendMsg($Send, 0x00F7, 0, $hBitmap)
 

Trans

Знающий
Сообщения
257
Репутация
6
Спасибо, разобрался... теперь буду вникать как добавить ещё одну картинку:smile:
 

madmasles

Модератор
Глобальный модератор
Сообщения
7,790
Репутация
2,323
Yashied,
Скажите, пожалуйста, значение 0x00F7 как-то связано с $META_CREATEPALETTE из GDIPConstants.au3 или это другая константа?
 

Trans

Знающий
Сообщения
257
Репутация
6
Ребят, а кто подскажет как сделать кнопку с jpg иконкой?
 

Yashied

Модератор
Команда форума
Глобальный модератор
Сообщения
5,379
Репутация
2,724
Также как и с PNG.
 
Верх