简体   繁体   English

如何使表格无边界透明?

[英]How to make the form transparent without the border?

I would like to know if it is possible to make the Form transparent (AlphaBlend) without the Border (where the minimize button is and all that) being transparent too? 我想知道是否有可能使窗体(AlphaBlend)透明, 边框(最小化按钮和所有其他功能)也透明吗? If it is, how can I do it? 如果是,该怎么办?

屏幕截图

It is possible, but any controls you put on such form will not be visible. 有可能,但是您放置在这种形式上的任何控件将不可见。

Here is some base code to get you started, but I have never used it on forms with border, so there might be possible issues with border functionality. 这是一些入门的基本代码,但是我从未在带边框的表单上使用过,因此边框功能可能存在问题。 Most likely, you will have to create bitmap that will include window border and set alpha for that part to 255; 最有可能的是,您将必须创建将包括窗口边框的位图,并将该部分的alpha设置为255;

procedure PremultiplyBitmap(Bitmap: TBitmap);
var
  Row, Col: Integer;
  p: PRGBQuad;
begin
  Bitmap.AlphaFormat := afPremultiplied;
  for Row := 0 to Bitmap.Height - 1 do
    begin
      Col := Bitmap.Width;
      p := Bitmap.ScanLine[Row];
      while (Col > 0) do
        begin
          p.rgbBlue := p.rgbReserved * p.rgbBlue div 255;
          p.rgbGreen := p.rgbReserved * p.rgbGreen div 255;
          p.rgbRed := p.rgbReserved * p.rgbRed div 255;
          inc(p);
          dec(Col);
        end;
    end;
end;

procedure PremultiplyBitmapAlpha(Bitmap: TBitmap; Alpha: byte);
var
  Row, Col: Integer;
  p: PRGBQuad;
begin
  Bitmap.AlphaFormat := afPremultiplied;
  for Row := 0 to Bitmap.Height - 1 do
    begin
      Col := Bitmap.Width;
      p := Bitmap.ScanLine[Row];
      while (Col > 0) do
        begin
          p.rgbReserved := Alpha;
          p.rgbBlue := p.rgbReserved * p.rgbBlue div 255;
          p.rgbGreen := p.rgbReserved * p.rgbGreen div 255;
          p.rgbRed := p.rgbReserved * p.rgbRed div 255;
          inc(p);
          dec(Col);
        end;
    end;
end;

procedure BlendForm(Form: TCustomForm; Bmp: TBitmap);
var
  BitmapPos: TPoint;
  BitmapSize: TSize;
  BlendFunction: TBlendFunction;
begin
   BitmapPos := Point(0, 0);
   BitmapSize.cx := Bmp.Width;
   BitmapSize.cy := Bmp.Height;

   BlendFunction.BlendOp := AC_SRC_OVER;
   BlendFunction.BlendFlags := 0;
   BlendFunction.SourceConstantAlpha := 255;
   BlendFunction.AlphaFormat := AC_SRC_ALPHA;

   UpdateLayeredWindow(Form.Handle, 0, nil, @BitmapSize, Bmp.Canvas.Handle, @BitmapPos, 0, @BlendFunction, ULW_ALPHA);
end;

procedure TForm1.CreateWnd;
var
  ExStyle: DWORD;
begin
  inherited;
  ExStyle := GetWindowLong(Handle, GWL_EXSTYLE);
  if (ExStyle and WS_EX_LAYERED = 0) then
    SetWindowLong(Handle, GWL_EXSTYLE, ExStyle or WS_EX_LAYERED);
end;

procedure TForm1.FormCreate(Sender: TObject);
var
  Bmp: TBitmap;
begin
  Bmp := TBitmap.Create;
  try
    Bmp.PixelFormat := pf32bit;
    Bmp.Width := ClientWidth;
    Bmp.Height := ClientHeight;
    PremultiplyBitmapAlpha(Bmp, 200);
    BlendForm(Form1, Bmp);
  finally
    Bmp.Free;
  end;
end;

Bitmaps you use have to be 32-bit bitmaps. 您使用的位图必须是32位位图。 If you want to blend whole bitmap with some alpha value, you can use PremultiplyBitmapAlpha procedure, and if your bitmap has alpha channel you can then use PremultiplyBitmap procedure. 如果要将整个位图与某些alpha值混合,则可以使用PremultiplyBitmapAlpha过程,如果位图具有alpha通道,则可以使用PremultiplyBitmap过程。

For speed improvements you can use premultiplied byte table like this: 为了提高速度,您可以使用预乘字节表,如下所示:

var
  PreMult: array[byte, byte] of byte;

procedure InitializePreMult;
var
  Row, Col: Integer;
begin
  // precalculate all possible values of a*b
  for Row := 0 to 255 do
    for Col := Row to 255 do
      PreMult[Row, Col] := Row*Col div 255;
end;

and then PremultiplyBitmap procedure would use that lookup table: 然后PremultiplyBitmap过程将使用该查找表:

procedure PremultiplyBitmap(Bitmap: TBitmap);
var
  Row, Col: integer;
  p: PRGBQuad;
begin
  for Row := 0 to Bitmap.Height-1 do
  begin
    Col := Bitmap.Width;
    p := Bitmap.ScanLine[Row];
    while (Col > 0) do
    begin
      p.rgbBlue := PreMult[p.rgbReserved, p.rgbBlue];
      p.rgbGreen := PreMult[p.rgbReserved, p.rgbGreen];
      p.rgbRed := PreMult[p.rgbReserved, p.rgbRed];
      inc(p);
      dec(Col);
    end;
  end;
end;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM