关于不规则图片,不规则窗口的问题。(100分)

  • 主题发起人 主题发起人 ruder
  • 开始时间 开始时间
R

ruder

Unregistered / Unconfirmed
GUEST, unregistred user!
现有一张矩形图片(bmp),我只想取其中的不是黑色的部分做为不规则图片生成同样大小的不规则窗体。
请问大虾们我该怎么做?有没有现成的控件?谢谢。
 
想取其中的不是黑色的部分做为一个区域保存:
unit _getrgn;

interface

uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
ExtDlgs, StdCtrls, ExtCtrls;

type
TForm1 = class(TForm)
Image1 : TImage;
btnOpen : TButton;
btnSave : TButton;
OpenPicDlg1 : TOpenPictureDialog;
SaveDlg1: TSaveDialog;
procedure btnSaveClick(Sender: TObject);
procedure btnOpenClick(Sender: TObject);

private
{ Private declarations }
public
{ Public declarations }
end;

function ysGetWindowRgn( Bmp :TBitmap; TransColor :TColor ): HRGN;
procedure ysSaveRgnToFile( Rgn :HRGN; SaveName :String );

var
Form1: TForm1;

implementation

{$R *.DFM}

function ysGetWindowRgn( Bmp :TBitmap; TransColor :TColor ): HRGN;
var
x,
y,
w,
h,
BeginPos,
EndPos : Integer;
Rgn1,
Rgn2 : HRGN;
begin
Rgn1 :=0;
Rgn2 :=0;

w :=Bmp.Width;
h :=Bmp.Height;

Result :=0;

for y :=0 to h -1 do
begin
x :=0;
EndPos :=0;

repeat
BeginPos :=x;
Inc( x );

while ( Bmp.Canvas.Pixels[x,y] <> TransColor ) and ( x <=w ) do
begin
Bmp.Canvas.Pixels[x,y] :=clBlue;
Inc( x );
end;

EndPos :=x;

if BeginPos <> w then
begin
if EndPos =w then Dec( EndPos );
if Rgn1 =0 then
Rgn1 :=CreateRectRgn( BeginPos +1, y, EndPos, y +1 )
else
begin
Rgn2 :=CreateRectRgn( BeginPos +1, y, EndPos, y +1 );
if Rgn2 <>0 then CombineRgn( Rgn1, Rgn1, Rgn2, RGN_OR );
DeleteObject( Rgn2 );
end;
end;

until x >= w -1;

end; // for 'for y :=0 to h -1 do...'

Result :=Rgn1;
end;

procedure ysSaveRgnToFile( Rgn :HRGN; SaveName :String );
var
RgnSize : Integer;
RgnData : pRGNDATA;
fm : TFileStream;
begin
try
fm :=TFileStream.Create( SaveName, fmCreate or fmShareDenyWrite );
except
ShowMessage( 'Error in create file ' +SaveName );
Exit;
end;

RgnSize :=GetRegionData( Rgn, 0, nil );
GetMem( RgnData, RgnSize );
GetRegionData( Rgn, RgnSize, RgnData );

fm.Write( RgnSize, Sizeof( RgnSize ) );
fm.Write( RgnData^, RgnSize );

FreeMem( RgnData, RgnSize );
fm.Free;
end;



procedure TForm1.btnSaveClick(Sender: TObject);
var
Rgn : HRGN;
begin
btnSave.Enabled :=false;

if SaveDlg1.Execute then
begin
Rgn :=ysGetWindowRgn( Image1.Picture.Bitmap,
Image1.Picture.Bitmap.Canvas.Pixels[1,1]
);
if Rgn <>0 then
ysSaveRgnToFile( Rgn, SaveDlg1.FileName )
else ShowMessage( 'Error in create window region.' );
end;

btnSave.Enabled :=true;
end;

procedure TForm1.btnOpenClick(Sender: TObject);
begin
if OpenPicDlg1.Execute then
Image1.Picture.LoadFromFile( OpenPicDlg1.FileName );
end;

end.
窗体:
object Form1: TForm1
Left = 192
Top = 107
AutoScroll = False
Caption = 'Form1'
ClientHeight = 169
ClientWidth = 407
Color = clBtnFace
Font.Charset = DEFAULT_CHARSET
Font.Color = clWindowText
Font.Height = -11
Font.Name = 'MS Sans Serif'
Font.Style = []
OldCreateOrder = False
Position = poScreenCenter
Scaled = False
PixelsPerInch = 96
TextHeight = 13
object Image1: TImage
Left = 16
Top = 16
Width = 128
Height = 128
AutoSize = True
end
object btnOpen: TButton
Left = 240
Top = 16
Width = 75
Height = 25
Caption = '&amp;Open'
TabOrder = 0
OnClick = btnOpenClick
end
object btnSave: TButton
Left = 240
Top = 112
Width = 75
Height = 25
Caption = '&amp;Save'
TabOrder = 1
OnClick = btnSaveClick
end
object OpenPicDlg1: TOpenPictureDialog
DefaultExt = '.bmp'
Filter =
'All (*.bmp;*.ico)|*.bmp;*.ico|Bitmaps (*.bmp)|*.bmp|Icons (*.ico' +
')|*.ico'
Left = 160
Top = 16
end
object SaveDlg1: TSaveDialog
DefaultExt = '.rgn'
Filter = 'Yafeisoft region file(*.rgn)|*.rgn'
Left = 160
Top = 48
end
end
 
从磁盘读取区域文件并设置窗体区域:
function ysLoadRgn( OpenName :String ):HRGN;

function ysLoadRgn( OpenName :String ):HRGN;
var
fm : TFileStream;
RgnSize : Integer;
RgnData : pRGNDATA;
wndRgn : HRGN;
begin
fm :=TFileStream.Create( OpenName, fmOpenRead );
fm.Read( RgnSize, Sizeof( RgnSize ) );

if not ( RgnSize <> 0 ) then
begin
ShowMessage( 'Error in read Yafeisoft region file.' );
Result :=0;
Exit;
end;

GetMem( RgnData, RgnSize );
fm.Read( RgnData^, RgnSize );
wndRgn :=ExtCreateRegion( nil, RgnSize, RgnData^ );

fm.Free;

if wndRgn <>0 then
Result :=wndRgn
else Result :=0;
end;

procedure TForm1.FormCreate(Sender: TObject);
var
Rgn : HRGN;
begin
Rgn :=ysLoadRgn( '1.rgn' );
if Rgn <> 0 then SetWindowRgn( Handle, Rgn, true ) else ShowMessage( 'xxx' );

end;
 
感谢flyinwuhan。
我刚涉及图象处理,前面的代码太多看的不是很明白,
能讲讲原理吗?
其实我要实现的效果很简单,
现在有一张巨型图片,包含不规则图形(在中间),外面的全部用黑色(或者蓝色)添充,
现在要把这个不规则图片显示到窗体上,窗体上已经有一张背景图,要求不破坏背景图,
不需要透明显示
 
>>生成同样大小的不规则窗体
到底要做不规则窗体还是在普通窗体上显示不规则图片啊?
>>窗体上已经有一张背景图,要求不破坏背景图,不需要透明显示......
不明白什么意思! 不透明显示必然破坏背景啊

 

Similar threads

后退
顶部