Hoffentlich die richtige Kategorie???
Hi,
ich brauch mal Hife zu 3 Problemen, aber erst einmal die Beschreibung was ich vor habe und was ich bereits wie gemacht habe und vor allem warum

Naja ich hab mir gedacht eine Art: "Informations Fenster" zu bauen, welches man z.b. bei Winamp findet oder diversen anderen Programmen...
Fenster sollte komplett grafisch sein und über einen Schlagschatten verfügen, wobei die Erstellung des Fensters(rund oder rechtwinkelig) kein Hinderniss sein sollte, soll heissen Fenster passt sich der Grafik an in jedem Fall...
Die Fenstereigenschaften:
1. Show
Show sollte über ein FadeIn Effekt verfügen inkl. Intervall. ( Intervall stellt die Zeit da, wie lange das Fenster sichtbar ist...)
2. Hide
Hide bewirkt den gegenteiligen Effekt von Show, also brauche ich hier ein FadeOut...
3. Textlänge
Fenster soll sich der Textlänge anpassen, heißt im Klartext: default Höhe + Breite, wenn Text länger als Fensterbreite, Fensterbreite anpassen...
Die 3 Fenstereigenschaften von oben sind zugleich auch meine 3 Probleme, daß hängt damit zusammen wie ich mein Fenster baue bzw. das Fenster an die Grafiken anpasse dazu jetzt mehr!
Winamp benutzt für sein: "Informations Fenster" 2 PNG Grafiken (zumindest beim Modern-Skin im Unter-Ordner 'Notifier') erstes PNG stellt ein abgerundetes Rechteck da, welches in der mitte einen komplexen Farbverlauf hat (also nicht wie üblich oft benutztes FromColor - ToColor

wobei der Farbverlauf selber nochmals einen 1px schwarzen Rand beinhaltet...
Das 2. PNG ist die Kopie des ersten PNG's aber inkl. Schlagschatten...
Jetzt sind wir bei nächsten Problem, da ich keine Ahnung habe wie ich ein PNG stretchen / shrinken soll, ohne diese zu einem Bitmap zu konvertieren und dabei sämtliche Transparenz zu verlieren, konnte ich logischer Weise nicht direkt die Winamp PNG's benutzen.
Also habe ich in Photoshop 2 Bitmaps erstellt, ähnlich der Winamp PNG's, der Hintergrund ist bei beiden schwarz.
Mein 2. Bitmap enthält den Schlagschatten und der Farbverlauf ist hier mit weiß übermalt, da weiß im 2. Bitmap die transparente Farbe darstellt...
Erstellt habe ich das 2. Bitmap einfach, in dem ich bei Photoshop in die Kanäle gewechselt bin dort den blauen Farbkanal dupliziert habe über Kopie erstellen als Neu. Danach nur noch Bild - Konvertieren 8Bit Graustufen und als Bitmap speichern auswählen (nein das ist kein neues Photoshop Tutorial hier

)
Jetzt, da ich nicht wußte was nun die beste Methode ist um eine TForm an ein Bitmap anzugleichen ( CreateRegion usw. ) habe ich mich dafür entschieden, folgende Funktionen zu benutzen, da ich grad einen netten QuellCode zur Hand hatte der genau das macht was ich eigentlich suchte folgendes wurde bentutzt:
1. LayeredWindows
2. TBlendFunktion Funktion
3. GR32 sowie GR32_Funktions Units (sind im Netz erhältlich...
4. AnimateWindows Funktion
Das Problem von den bentuzen Funktionen ist folgendes (vielleicht auch anhand des unten stehenden Quelltextes ersichtlich) das ich weder über ein AnimateWindow ein Fading hinbekomme, noch einen Text auf das Fenster über DrawText, DrawTextEx usw zeichnen kann,,,
Das Fading sollte übrigens im eigenen Thread laufen da glaub ich beim Fading die Anwengung einfriert....
Vielleicht kann sich jemand mal den Quelltext ansehen, Verbesserungen vorschlagen oder mir sagen wie man das ganze wesentlich vereinfachen könnte?
Ich wäre super dankbar dafür aber bitte keine postings zu Komponenten oder so, da ich das selber lernen muss / will ...
Bei Interesse oder zum testen kann ich gerne das ganze Projekt inkl. der beiden Bitmaps zusenden, mir ist jedes Mittel recht um das endlich abschliessen zu können, da ich noch diverse andere Sachen bauen muss und mich nicht Monate lang damit beschäftigen kann leider
Der Code: ( Vorsicht Chaos am Werk! )
Delphi-Quellcode:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, GR32, GR32_Filters, ExtCtrls, StdCtrls;
type
TFadeThread =
Class(TThread)
private
FLayeredWindow : TForm;
protected
procedure Execute;
override;
public
constructor Create(aLayeredWindow: TForm);
procedure AnimateSafe(hWnd: HWND; dwTime: DWord; dwFlags: DWord);
published
end;
type
TForm1 =
class(TForm)
Label1: TLabel;
Label2: TLabel;
procedure FormCreate(Sender: TObject);
procedure FormShow(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
FFadeThread: TFadeThread;
FTop : Integer;
FOffsetX,
FOffsetY : Integer;
procedure DoShow;
procedure CreateParams(
var Params: TCreateParams);
override;
procedure ThreadDone(Sender: TObject);
end;
var
Form1: TForm1;
AlphaBmp, SkinBmp: TBitmap32;
TopLeft, BmpTopLeft: TPoint;
WorkBmp: TBitmap;
BmpSize: TSize;
DC: HDC;
C : Integer;
Blend: TBlendFunction;
implementation
{$R *.dfm}
type
TFadeThreadDone =
procedure(Sender: TObject)
of object;
const
WS_EX_LAYERED = $80000;
AC_SRC_OVER = $0;
AC_SRC_ALPHA = $1;
AC_SRC_NO_PREMULT_ALPHA = $1;
AC_SRC_NO_ALPHA = $2;
AC_DST_NO_PREMULT_ALPHA = $10;
AC_DST_NO_ALPHA = $20;
LWA_COLORKEY = $1;
LWA_ALPHA = $2;
ULW_COLORKEY = $1;
ULW_ALPHA =$2;
ULW_OPAQUE = $4;
function SetLayeredWindowAttributes(hwnd: HWND; crKey: TColor; bAlpha: byte;
dwFlags: DWORD): BOOL;
stdcall;
external '
user32.dll';
function UpdateLayeredWindow(hwnd: HWND; hdcDst: HDC; pptDst: PPoint;
psize: PSize; hdcSrc: HDC; pptSrc: PPoint; crKey: TColor;
pblend: PBlendFunction; dwFlags: DWORD): BOOL;
stdcall;
external '
user32.dll';
procedure TFadeThread.AnimateSafe(hWnd: HWND; dwTime: DWord; dwFlags: DWord);
type
d =
function(a: THandle; b, c: DWord): Boolean;
stdcall;
var
e : integer;
g: d;
begin
try
e := LoadLibrary('
user32.dll');
if e = 0
then
exit
else
begin
g := GetProcAddress(e, '
AnimateWindow');
if @g =
nil then
exit
else
begin
g(hWnd, dwTime, dwFlags);
end;
end;
finally
FreeLibrary(e);
end;
end;
procedure TForm1.CreateParams(
var Params: TCreateParams);
begin
inherited CreateParams(Params);
Params.ExStyle := Params.ExStyle
or WS_EX_APPWINDOW
and not WS_EX_TOOLWINDOW;
end;
constructor TFadeThread.Create(aLayeredWindow: TForm);
begin
inherited Create(False);
FLayeredWindow := aLayeredWindow;
FreeOnTerminate := True;
end;
procedure TFadeThread.Execute;
begin
// AnimateSafe(Form1.Handle, 3000, AW_BLEND);
{ above does not work cauze can't fade out!, also
I can make it FadeIn but I lose all Graphics, fadin will fade my Window but without any Graphics...
with FFadeThread := TFadeThread.Create(TForm) do
begin
FFadeThread.terminate := ThreadDone }
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
SetWindowLong(
Handle, GWL_EXSTYLE, WS_EX_LAYERED);
SetWindowLong(Application.Handle, GWL_EXSTYLE,
GetWindowLong(Application.Handle, GWL_EXSTYLE)
or
WS_EX_TOOLWINDOW
and not WS_EX_APPWINDOW);
WorkBmp :=
nil;
AlphaBmp :=
nil;
SkinBmp :=
nil;
try
WorkBmp := TBitmap.Create;
with WorkBmp, Canvas, BmpSize
do
begin
cx := ClientWidth;
cy := ClientHeight;
PixelFormat := pf32Bit;
Width := cx;
Height := cy;
end;
AlphaBmp := TBitmap32.Create;
AlphaBmp.LoadFromFile('
Mask2.bmp');
SkinBmp := TBitmap32.Create;
with SkinBmp
do
begin
LoadFromFile('
hint2.bmp');
IntensityToAlpha(SkinBmp, AlphaBmp);
DrawTo(WorkBmp.Canvas.Handle, 0, 0);
end;
TopLeft := BoundsRect.TopLeft;
BmpTopLeft := Point(0, 0);
DC := GetDC(0);
if not Win32Check(LongBool(
DC))
then
RaiseLastWin32Error;
with Blend
do
begin
BlendOp := AC_SRC_OVER;
BlendFlags := 0;
SourceConstantAlpha := 255;
AlphaFormat := AC_SRC_ALPHA;
end;
if not Win32Check(UpdateLayeredWindow(
Handle,
DC, @TopLeft, @BmpSize,
WorkBmp.Canvas.Handle, @BmpTopLeft, clNone, @Blend, ULW_ALPHA))
then
RaiseLastWin32Error;
finally
WorkBmp.Free;
AlphaBmp.Free;
SkinBmp.Free;
end;
end;
procedure TForm1.DoShow;
var
R: TRect;
TP: integer;
WND: THandle;
begin
WND := GetFocus;
FOffsetX := 0;
FOffsetY := 0;
SystemParametersInfo( SPI_GETWORKAREA, 0, @R, 0);
TP := FTop;
TP := R.Bottom - Form1.Height + FOffsetX;
Form1.Left := R.Right - Form1.Width - 2 + FOffsetY;
Form1.Top := R.Bottom;
SetWindowPos(Form1.Handle, HWND_TOPMOST, 0, 0, 0, 0,
SWP_SHOWWINDOW
or SWP_NOACTIVATE
or SWP_NOSIZE
or SWP_NOMOVE);
Form1.Top :=
TP;
Windows.SetFocus( WND );
end;
procedure TForm1.ThreadDone(Sender: TObject);
begin
FFadeThread :=
nil;
end;
procedure TForm1.FormShow(Sender: TObject);
begin
DoShow;
end;
end.