Autor Beitrag
JayEff
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2971

Windows Vista Ultimate
D7 Enterprise
BeitragVerfasst: Fr 02.03.07 01:01 
Eine Bitmap abgestuft grauer werden lassen

Ihr kennt doch den Effekt, den Windows beim Anzeigen des "Herunterfahren"-Menüs einsetzt. Der Hintergrund graut langsam aus.
Ich habe diesen Effekt mal implementiert:
ausblenden volle Höhe Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
//Parameter:
//  Bitmap:     Das Bild, welches ausgegraut werden soll. Wird verändert!
//              Bei jedem Schritt muss das unveränderte Original-Bitmap übergeben werden!
//  Step:       Der aktuelle Schritt mit einem Wert zwischen 0 und StepsCount
//  StepsCount: Die Gesamtzahl der Schritte, die gemacht werden sollen
//  darkness:   Ein zusätzlicher Wert für Dunkelheit, damit auch Weiß grau wird.
procedure greyout(Bitmap: TBitmap; step, StepsCount: Integer; darkness: byte = 0);
type
  pixel = Array[0..2Of byte;
var
  p: ^pixel;
  x, y, temp: Integer;
  median, redstep, bluestep, greenstep: byte;
begin
  Bitmap.PixelFormat := pf24Bit;
  if step > stepsCount then
    step := StepsCount;
  for y := 0 to Bitmap.Height - 1 do
  Begin
    p := Bitmap.ScanLine[y];
    for x := 0 to Bitmap.Width - 1 do
    begin
      temp := ((p^[0] + p^[1] + p^[2]) Div 3) - darkness;
      if temp < 0 then
        temp := 0;

      median := temp;

      redstep := (median - p^[0]) Div StepsCount;
      bluestep := (median - p^[1]) Div StepsCount;
      greenstep := (median - p^[2]) Div StepsCount;

      p^[0] := p^[0] + redstep * step;
      p^[1] := p^[1] + bluestep * step;
      p^[2] := p^[2] + greenstep * step;

      inc(p);
    end;
  end;
end;


Zur Erklärung:
Bitmap soll natürlich die zu verändernde Bitmap darstellen.

Wie schon im Titel angegeben, lässt sich der Effekt abgestuft darstellen, wobei StepsCount die Anzahl der Abstufungen darstellt.

Steps soll von 0 bis StepsCount erhöht werden, dieser Parameter sagt aus, der wievielte Schritt bei der Abstufung zurückgegeben wird.

darkness ist der Wert, um den die entgülige Farbe noch verdunkelt wird, damit z.B. die Farbe Weiß auch ausgegraut wird und nicht Weiß bleibt ( (255+255+255) /3 = 255 => Weiß bleibt Weiß). Darkness hat den Standartwert 0, man muss diesen Parameter also garnicht angeben. In diesem Fall wird Weiß dann Weiß bleiben. Man sollte Darkness vielleicht nicht größer als 100 wählen, da sonst schnell das gesamte bild am Ende schwarz ist. Einfach mal damit rumspielen, bis der gewünschte Effekt erreicht wird!


Zur Verwendung:
Man nehme einen TTimer und eine globale Variable var x: integer;.

ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
procedure TForm1.Timer1Timer(Sender: TObject);
begin
   Image1.Picture.Bitmap.LoadFromFile(Filename);
   grayout(Image1.Picture.Bitmap, x, 30);
   inc(x);
   if x > 30 then 
     Timer1.Enabled := false;
end;

So, oder so ähnlich kann der Effekt implementiert werden. Eine Abstufung von 30 Schritten ist schon recht fein.
Die Bitmap muss natürlich nicht immerwieder erneut von der Festplatte geladen werden, sinnvoller ist es sicher, den Inhalt im Speicher zu halten und von diesem neu zu laden; evtl. ein weiteres TBitMap Objekt zur Speicherung der Originaldaten anlegen. Alternativ kann man natürlich auch Speicheroptimiert arbeiten, und das Bild von der Festplatte neu laden, wie in meinem Beispiel.

PS: Falls ich mich bei der Reihenfolge von grün/rot/blau im array[0..2] of Byte geirrt haben sollte, meldet mir das doch bitte, so dass ich es korrigieren kann :) Das passiert mir immer wieder...

_________________
>+++[>+++[>++++++++<-]<-]<++++[>++++[>>>+++++++<<<-]<-]<<++
[>++[>++[>>++++<<-]<-]<-]>>>>>++++++++++++++++++.+++++++.>++.-.<<.>>--.<+++++..<+.


Zuletzt bearbeitet von JayEff am So 18.03.07 23:00, insgesamt 3-mal bearbeitet