Witam.
Mam za zadanie napisać w Delphi programy, który rysuje podaną ilość okręgów, tak aby żadne się nie przecinały. Moja forma to jedno pole edycyjne - wczytuje ilość okręgów i jeden button - rysuj. Napotkałem następujące problemy, z którymi nie potrafię sobie poradzić:
-
Czy jest możliwość rysowania tylko konturów? Dotychczas Rysowałem za pomocą Canvas.Ellipse(); i większe okręgi przykrywają mi mniejsze - muszę je sortować, aby wszystko było jak należy.
-
Oba komponenty mam u góry formy i czasem okręgi na nie wjeżdżają - jak obliczyć miejsce, od którego mogę zacząć rysować - czyli gdzie kończą się komponenty.
-
Po kilkunastym kliknięciu buttona program zawiesza się.
-
Na raz rysuje tylko jeden okrąg. Dlaczego?
Dorzucam źródło:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls;
const
M = 1000;
type
TForm1 = class(TForm)
Button1: TButton;
LabeledEdit1: TLabeledEdit;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
type
okrag = record
x : integer;
y : integer;
r : integer;
end;
var
Form1: TForm1;
ile, n, a, b : integer;
tablica : array[0..M] of okrag;
o : okrag;
implementation
{$R *.dfm}
function odcinek(o1, o2 : okrag) : real;
var
a, b : integer;
begin
a := abs(o1.x - o2.x);
b := abs(o1.y - o2.y);
odcinek := sqrt(a * a + b * b);
end;
function rozlaczne(o: okrag) : boolean;
var
i : integer;
dl : real;
w : boolean;
begin
w := false;
for i := 0 to ile do
begin
dl := odcinek(o, tablica[i]);
if not ((dl < abs(o.r - tablica[i].r)) or (dl > o.r + tablica[i].r)) then
begin
w := false;
break;
end
else
w := true;
end;
rozlaczne := w;
end;
function min(w1, w2 : integer) : integer;
begin
if w1 < w2 then
min := w1
else
min := w2;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
randomize;
n := StrToInt(LabeledEdit1.Text);
o.x := 0;
o.y := 0;
o.r := 0;
for ile :=0 to M do
tablica[ile] := o;
for ile := 0 to n - 1 do
begin
o.x := random(Width - 10) + 5;
o.y := random(Height - 66) + 61;
a := min(o.x, Width - o.x);
b := min(o.y, Height - 56 - o.y);
a := min(a, b);
o.r := random(a - 5) + 5;
while not rozlaczne(o) do
o.r := random(a - 5) + 5;
tablica[ile] := o;
end;
{sortowanie wg promienia, aby wieksze okregi nie przykrywaly mniejszych}
Canvas.rectangle(0, 0, Width, Height);
for ile := 0 to n - 1 do
Canvas.Ellipse(o.x - o.r, o.y - o.r, o.x + o.r, o.y + o.r);
end;
end.