![]() |
|
|
|||||||
| Регистрация | << Правила форума >> | FAQ | Пользователи | Календарь | Поиск | Сообщения за сегодня | Все разделы прочитаны |
![]() |
|
|
Опции темы | Поиск в этой теме | Опции просмотра |
|
#1
|
||||
|
||||
|
Доброго времени суток, нарисовал закручивающуюся черную дыру, теперь хочу закрасить завитки, но не очень четко понимаю как работает функция FloodFill и какой формулой описать точку закрашивания. Помогите пожалуйста.
![]() Код:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, math;
type
TForm1 = class(TForm)
PB1: TPaintBox;
B1: TButton;
Edit1: TEdit;
Edit2: TEdit;
Edit3: TEdit;
Timer1: TTimer;
procedure B1Click(Sender: TObject);
procedure Timer1Timer(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
x, y, x1, y1, x2, y2, x3, y3, x4, y4, r, r1, i: Integer;
Alpha,Alpha1: Real;
implementation
{$R *.dfm}
procedure TForm1.B1Click(Sender: TObject);
begin
x:=Round(PB1.Width/2);
y:=Round(PB1.Height/2);
r:=150;
r1:=100;
Alpha:=0;
Timer1.Enabled:=true;
end;
procedure TForm1.Timer1Timer(Sender: TObject);
begin
PB1.Canvas.Pen.Color:=clBtnFace;
PB1.Canvas.Brush.Style:=bsSolid;
PB1.Canvas.Brush.Color:=clBtnFace;
PB1.Canvas.FillRect(Rect(0,0 , PB1.Width,PB1.Height));
If (Alpha>=2*pi) then Alpha:=0;
Alpha:=Alpha+pi/180;
Alpha1:=Alpha;
PB1.Canvas.Pen.Width:=2;
PB1.Canvas.Pen.Color:=clPurple;
PB1.Canvas.Brush.Color:=clPurple;
For i:=1 to 12 do
begin
x1:=x+Round(Cos(Alpha1)*r1);
y1:=y+Round(Sin(Alpha1)*r1);
x2:=x+Round(Cos(Alpha1+190*(pi/180))*r1);
y2:=y+Round(Sin(Alpha1+190*(pi/180))*r1);
x3:=x+Round(Cos(Alpha1-25*(pi/180))*20*r1);
y3:=y+Round(Sin(Alpha1-25*(pi/180))*20*r1);
x4:=x+Round(Cos(Alpha1+25*(pi/180))*20*r1);
y4:=y+Round(Sin(Alpha1+25*(pi/180))*20*r1);
If (i Mod 2=0) then
begin
PB1.Canvas.Arc(x1-r,y1-r,x1+r,y1+r , x2,y2,x3,y3); //Внешняя
end
else
begin
PB1.Canvas.Arc(x1-r,y1-r,x1+r,y1+r , x2,y2,x4,y4);
end;
Alpha1:=Alpha1+(360/12)*(pi/180);
end;
end;
end.Delphi BlackHole.rar //======Проект====== |
|
#2
|
||||
|
||||
|
Используй так:
Код:
FloodFill(x, y, Pixels[x, y], fsSurface); |
|
#3
|
||||
|
||||
|
Так, а Х и У - координаты точки внутри каждого "лепестка" ? Если да то помогите с формулой для этого.
|
|
#4
|
|||
|
|||
|
если не охота вычислять, то можно первый fillrect делать цветом лепестков
а после – floodfill цветом фона, и центр, если надо |
|
#5
|
||||
|
||||
|
К сожалению я планирую сделать из этого класс и встроить другую прогамму, где на канве будут другие объекты, так что этото способ не подходит. Но это неплохая мысль.
|
|
#6
|
|||
|
|||
|
тогда рисовать на невидимом bitmap, и после copyrect на ту канву
|
|
#7
|
||||
|
||||
|
Спасибо, очень дельный совет, это решает сразу много проблем и убирает эпилепсию из моего проекта...
Скажите а как отучить делфи убирать TBitMap, если он не прикреплен к другим объектам? А то я ведь однажды нечаянно нажму да... ![]() |
|
#8
|
||||
|
||||
|
перенести объявление TBitmap в { Private declarations } секцию или { Public declarations } секцию
|
|
#9
|
||||
|
||||
|
Благодарю, работает отлично, тему можно закрывать.
Вот, что получилось: Delphi BlackHole.rar Код:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, math;
type
TForm1 = class(TForm)
PB1: TPaintBox;
B1: TButton;
Edit1: TEdit;
Edit2: TEdit;
Edit3: TEdit;
Timer1: TTimer;
procedure B1Click(Sender: TObject);
procedure Timer1Timer(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
BM1: TBitMap;
end;
var
Form1: TForm1;
x, y, x1, y1, x2, y2, x3, y3, x4, y4, r, r1, i: Integer;
Alpha,Alpha1: Real;
implementation
{$R *.dfm}
procedure TForm1.B1Click(Sender: TObject);
begin
BM1:=TBitMap.Create;
BM1.Height:=601;
BM1.Width:=601;
x:=Round(PB1.Width/2);
y:=Round(PB1.Height/2);
r:=200; //150
r1:=100;
Alpha:=0;
Timer1.Enabled:=true;
end;
procedure TForm1.Timer1Timer(Sender: TObject);
begin
BM1.Canvas.Pen.Width:=3;
BM1.Canvas.Brush.Color:=clBlack;
BM1.Canvas.FillRect(Rect(0,0 , BM1.Width,BM1.Height));
If (Alpha>=2*pi) then Alpha:=0;
Alpha:=Alpha+pi/180;
Alpha1:=Alpha;
For i:=1 to 12 do
begin
x1:=x+Round(Cos(Alpha1)*r1);
y1:=y+Round(Sin(Alpha1)*r1);
x2:=x+Round(Cos(Alpha1+190*(pi/180))*3*r1);
y2:=y+Round(Sin(Alpha1+190*(pi/180))*3*r1);
x3:=x+Round(Cos(Alpha1-21*(pi/180))*20*r1); //20
y3:=y+Round(Sin(Alpha1-21*(pi/180))*20*r1);
x4:=x+Round(Cos(Alpha1+21*(pi/180))*20*r1); //25
y4:=y+Round(Sin(Alpha1+21*(pi/180))*20*r1);
If (i Mod 2=0) then
begin
BM1.Canvas.Pen.Color:=clSkyBlue;
BM1.Canvas.Brush.Color:=clSkyBlue;
BM1.Canvas.Arc(x1-r,y1-r,x1+r,y1+r , x2,y2,x3,y3); //Внешняя
end
else
begin
BM1.Canvas.Pen.Color:=clSkyBlue;
BM1.Canvas.Brush.Color:=clSkyBlue;
BM1.Canvas.Arc(x1-r,y1-r,x1+r,y1+r , x2,y2,x4,y4);
end;
Alpha1:=Alpha1+(360/12)*(pi/180);
end;
BM1.Canvas.Brush.Color:=clWhite;
BM1.Canvas.FloodFill(x, y, BM1.Canvas.Pixels[x, y], fsSurface);
BM1.Canvas.FloodFill(1, 1, BM1.Canvas.Pixels[1, 1], fsSurface);
BM1.Canvas.FloodFill(BM1.Height-1, 1, BM1.Canvas.Pixels[BM1.Height-1, 1], fsSurface);
BM1.Canvas.FloodFill(BM1.Height-1, BM1.Width-1, BM1.Canvas.Pixels[BM1.Height-1, BM1.Width-1], fsSurface);
BM1.Canvas.FloodFill(1, BM1.Width-1, BM1.Canvas.Pixels[1, BM1.Width-1], fsSurface);
PB1.Canvas.CopyRect(Rect(Point(0,0),Point(90,70)), BM1.Canvas, BM1.Canvas.ClipRect);
end;
end. |