Ветеран
Сообщения: 1264
Благодарности: 1024
|
Профиль
|
Отправить PM
| Цитировать
Цитата diman_21Ru:
Какой самый простой способ добавление всплывчатой картинки и с затуханием »
|
diman_21Ru, сплэш для битмапов, в том числе и c premultiplied alpha.
читать дальше »
Код:
[Setup]
AppName=test
AppVerName=test
DefaultDirName={tmp}
CreateAppDir=no
Uninstallable=no
CreateUninstallRegKey=no
BitmapResource=splash:compiler:WizModernImage.bmp
[Languages]
Name: ru; MessagesFile: compiler:Languages\russian.isl
[code]
#define A = (Defined UNICODE) ? "W" : "A"
const
AC_SRC_OVER = $0;
AC_SRC_ALPHA = $1;
ULW_ALPHA = $2;
SM_CXSCREEN = 0;
SM_CYSCREEN = 1;
WS_EX_LAYERED = $80000;
GWL_EXSTYLE = (-20);
WM_CLOSE = $10;
type
BLENDFUNCTION = record
BlendOp: Byte;
BlendFlags: Byte;
SourceConstantAlpha: Byte;
AlphaFormat: Byte;
end;
TIMERPARAM = record // user defined
bmp: TBitmap;
bf: BLENDFUNCTION;
dwStart: DWORD;
dwFadeIn: DWORD;
dwNormal: DWORD;
dwFadeOut: DWORD;
end;
// Window Functions
function UpdateLayeredWindow(hwnd: HWND; hdcDst: THandle; pptDst, psize: TPoint; hdcSrc: THandle; pptSrc: TPoint; crKey: DWORD; pblend: BLENDFUNCTION; dwFlags: DWORD): BOOL; external 'UpdateLayeredWindow@user32.dll stdcall delayload';
// Configuration Reference
function GetSystemMetrics(nIndex: Integer): Integer; external 'GetSystemMetrics@user32.dll stdcall';
// Large Integer Functions
function MulDiv(nNumber, nNumerator, nDenominator: Integer): Integer; external 'MulDiv@kernel32.dll stdcall';
// Window Class Functions
function GetWindowLong(hWnd: HWND; nIndex: Integer): Longint; external 'GetWindowLong{#A}@user32.dll stdcall';
function SetWindowLong(hWnd: HWND; nIndex: Integer; dwNewLong: Longint): Longint; external 'SetWindowLong{#A}@user32.dll stdcall';
// Time Functions
function GetSystemTimeAdjustment(var lpTimeAdjustment, lpTimeIncrement, lpTimeAdjustmentDisabled: DWORD): BOOL; external 'GetSystemTimeAdjustment@kernel32.dll stdcall';
function GetTickCount: DWORD; external 'GetTickCount@kernel32.dll stdcall';
// Timer Functions
function SetTimer(hWnd: HWND; var nIDEvent: TIMERPARAM; uElapse: UINT; lpTimerFunc: Longint): UINT_PTR; external 'SetTimer@user32.dll stdcall';
function KillTimer(hWnd: HWND; var uIDEvent: TIMERPARAM): BOOL; external 'KillTimer@user32.dll stdcall';
/////////////////////////////////////////////////////////////////////////////////////////
procedure SplashTimerProc(hwnd: HWND; uMsg: UINT; var wParam: TIMERPARAM; dwTime: DWORD);
var
dwCurrentTime: DWORD;
ptSize, ptSrc, ptDst: TPoint;
begin
{ get coords }
ptDst.x := (GetSystemMetrics(SM_CXSCREEN) - wParam.bmp.Width) shr 1;
ptDst.y := (GetSystemMetrics(SM_CYSCREEN) - wParam.bmp.Height) shr 1;
ptSize.x := wParam.bmp.Width;
ptSize.y := wParam.bmp.Height;
{ current time }
dwCurrentTime := dwTime - wParam.dwStart;
{ kill timer }
if dwCurrentTime > wParam.dwFadeIn + wParam.dwNormal + wParam.dwFadeOut then
begin
KillTimer(hwnd, wParam);
SendMessage(hwnd, WM_CLOSE, 0, 0);
end;
{ fade in }
if dwCurrentTime < wParam.dwFadeIn then
begin
wParam.bf.SourceConstantAlpha := MulDiv($FF, dwCurrentTime, wParam.dwFadeIn + 1);
UpdateLayeredWindow(hwnd, 0, ptDst, ptSize, wParam.bmp.Canvas.Handle, ptSrc, 0, wParam.bf, ULW_ALPHA);
end;
{ normal }
if (dwCurrentTime > wParam.dwFadeIn) and (dwCurrentTime < wParam.dwFadeIn + wParam.dwNormal) then
begin
wParam.bf.SourceConstantAlpha := $FF;
UpdateLayeredWindow(hwnd, 0, ptDst, ptSize, wParam.bmp.Canvas.Handle, ptSrc, 0, wParam.bf, ULW_ALPHA);
end;
{ fade out }
if dwCurrentTime > wParam.dwFadeIn + wParam.dwNormal then
begin
wParam.bf.SourceConstantAlpha := $FF - MulDiv($FF, dwCurrentTime - wParam.dwFadeIn - wParam.dwNormal, wParam.dwFadeOut + 1);
UpdateLayeredWindow(hwnd, 0, ptDst, ptSize, wParam.bmp.Canvas.Handle, ptSrc, 0, wParam.bf, ULW_ALPHA);
end;
end;
/////////////////////////////////////////////////////
function GetBitmapBitCount(const bmp: TBitmap): WORD;
var
MemStream: TMemoryStream;
szBuffer: String;
begin
Result := -1;
MemStream := TMemoryStream.Create;
try
bmp.SaveToStream(MemStream);
MemStream.Position := $1C; // biBitCount member of BITMAPINFOHEADER struct offset
szBuffer := StringOfChar(#0, 1);
if MemStream.Read(szBuffer, 1) = 1 then
Result := Ord(szBuffer[1]);
finally
MemStream.Free;
end;
end;
/////////////////////////////////////////////////////////////////
procedure ShowSplash(const dwFadeIn, dwNormal, dwFadeOut: DWORD);
// dwFadeIn..: fade in stage in ms
// dwNormal..: normal stage in ms
// dwFadeOut : fade out stage in ms
var
lpTimeAdjustment, lpTimeIncrement, lpTimeAdjustmentDisabled: DWORD;
tp: TIMERPARAM;
begin
if WizardSilent then Exit;
{ load bitmap }
tp.bmp := TBitmap.Create;
TBitmap(tp.bmp).LoadFromResourceName(HInstance, '_IS_SPLASH');
{ get bitmap bit count }
case GetBitmapBitCount(tp.bmp) of
-1: begin
tp.bmp.Free;
Exit;
end;
32: tp.bf.AlphaFormat := AC_SRC_ALPHA;
end;
{ create splash form }
with TForm.Create(nil) do
begin
BorderStyle := bsNone;
FormStyle := fsStayOnTop;
Position := poScreenCenter;
{ set dimensions }
Width := tp.bmp.Width;
Height := tp.bmp.Height;
{ set layered exstyle }
SetWindowLong(Handle, GWL_EXSTYLE, GetWindowLong(Handle, GWL_EXSTYLE) or WS_EX_LAYERED);
{ get minimal timer interval }
GetSystemTimeAdjustment(lpTimeAdjustment, lpTimeIncrement, lpTimeAdjustmentDisabled);
{ fill user defined struct }
tp.bf.BlendOp := AC_SRC_OVER;
tp.dwStart := GetTickCount;
tp.dwFadeIn := dwFadeIn;
tp.dwNormal := dwNormal;
tp.dwFadeOut := dwFadeOut;
{ start timer }
SetTimer(Handle, tp, lpTimeIncrement div 10000, CallbackAddr('SplashTimerProc'));
{ show form }
ShowModal;
{ cleanup }
tp.bmp.Free;
Free;
end;
end;
//////////////////////////////////
function InitializeSetup: Boolean;
begin
ShowSplash(1000, 2000, 1000);
Result := True;
end;
Цитата VoLT:
И так этот замечательный код (написанный на Delphi) позволяет вам вызвать ЛЮБУЮ функцию из вашего скрипта! »
|
VoLT, во-первых, тестовый скрипт ведет к AV, во-вторых, никакой это не callback.
|