Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2007.02.25;
Скачать: [xml.tar.bz2];

Вниз

Полигоны   Найти похожие ветки 

 
tio   (2007-01-01 10:42) [0]

С новым Годом!
Уважаемые мастера скажите, что надо сделать?:
Рисую 2 полигона с произвольными координатами,
и получается, что один частично закрывает другого.
Можно, чтобы полигон имел не один цвет, а при
наложении заливал ту область другим цветом.
Сделал через pixels, но очень долго.
Заранее спасибо.


 
Vovan #2   (2007-01-01 14:13) [1]

>Сделал через pixels, но очень долго.

Надо бы через Scanline.


 
Igor_Z   (2007-01-01 16:13) [2]

private
  procedure MAn;

var
 Form1: TForm1;

type
 TRGB = record
   b, g, r: byte;
 end;
 ARGB = array[0..1] of TRGB;
 PARGB = ^ARGB;

var
 b: TBitMap;
 p: PARGB;

implementation

{$R *.dfm}
function DotInRgn(TestPolygon : array of TPoint; const P : TPoint): boolean;
var
  ToTheLeftofPoint, ToTheRightofPoint : byte;
  np : integer;
  OpenPolygon : boolean;
  XIntersection : real;
begin
  ToTheLeftofPoint := 0;
  ToTheRightofPoint := 0;
  OpenPolygon := False;
  if not ((TestPolygon[0].X = TestPolygon[High(TestPolygon)].X) and
    (TestPolygon[0].Y = TestPolygon[High(TestPolygon)].Y)) then
    OpenPolygon := True;
  for np := 1 to High(TestPolygon) do
    if ((TestPolygon[np - 1].Y <= P.Y) and
      (TestPolygon[np].Y > P.Y)) or
      ((TestPolygon[np - 1].Y > P.Y) and
      (TestPolygon[np].Y <= P.Y))
      then
    begin
      XIntersection := TestPolygon[np - 1].X +
        ((TestPolygon[np].X - TestPolygon[np - 1].X) /
        (TestPolygon[np].Y - TestPolygon[np - 1].Y)) * (P.Y - TestPolygon[np - 1].Y);
     if XIntersection < P.X then Inc(ToTheLeftofPoint);
      if XIntersection > P.X then Inc(ToTheRightofPoint);
    end;
  if OpenPolygon then
  begin
    np := High(TestPolygon);
    if ((TestPolygon[np].Y <= P.Y) and
      (TestPolygon[0].Y > P.Y)) or
      ((TestPolygon[np].Y > P.Y) and
      (TestPolygon[0].Y <= P.Y)) then
    begin
      XIntersection := TestPolygon[np].X +
        ((TestPolygon[0].X - TestPolygon[np].X) /
        (TestPolygon[0].Y - TestPolygon[np].Y)) * (P.Y - TestPolygon[np].Y);
      if XIntersection < P.X then Inc(ToTheLeftofPoint);
      if XIntersection > P.X then Inc(ToTheRightofPoint);
    end;
  end;
  if (ToTheLeftofPoint mod 2 = 1) and (ToTheRightofPoint mod 2 = 1) then Result := True
  else
    Result := False;
end;

procedure TForm1.MAn;
var x,y:array[0..2] of TPoint;
i,j:integer;
begin
Canvas.Brush.Color:=clyellow;
x[0].X:=300;
x[1].X:=300;
x[2].X:=width;
x[0].Y:=500;
x[1].Y:=200;
x[2].Y:=0;
Canvas.Polygon(x);
y[0].X:=200;
y[1].X:=300;
y[2].X:=width;
y[0].Y:=550;
y[1].Y:=250;
y[2].Y:=100;
Canvas.Brush.Color:=cllime;
Canvas.Polygon(y);
b.TransparentColor:=clwhite;
b.Transparent:=true;
for j := 0 to b.height - 1 do
begin
if b.Canvas.Brush.Color = clwhite then
p := b.scanline[j];
for i:=0 to b.Width-1 do
if b.Canvas.Brush.Color = clwhite then
if (DotInRgn(x,Point(i,j))= true) and (DotInRgn(y,Point(i,j))= true) then
begin
p[i].r := random(125);
p[i].g := random(120);
p[i].b := random(100);
end;
end;
canvas.draw(0, 0, b);
end;

procedure TForm1.FormPaint(Sender: TObject);
begin
b := TBitMap.Create;
b.pixelformat := pf24bit;
b.width := Clientwidth;
b.height := Clientheight;
man;
b.Free;
end;

procedure TForm1.FormResize(Sender: TObject);
begin
refresh;
end;

Как-то все равно медленно.


 
Vovan #2   (2007-01-01 18:39) [3]


unit unitMain;

interface

uses
 Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
 Dialogs;

type
 TformMain = class(TForm)
   procedure FormPaint(Sender: TObject);
   procedure FormResize(Sender: TObject);
   procedure FormCreate(Sender: TObject);
   procedure FormDestroy(Sender: TObject);
 private
   { Private declarations }
 public
   procedure Man;
 end;

var
 formMain: TformMain;

type
TRGB = packed record
  b, g, r: byte;
end;

const
 PixelCountMax = 32768;

type
 pRGBArray = ^TRGBArray;
 TRGBArray = array[0..PixelCountMax-1] of TRGB;

var
b: TBitMap;

implementation

{$R *.dfm}

function DotInRgn(TestPolygon: array of TPoint; const P : TPoint): boolean;
var
 ToTheLeftofPoint, ToTheRightofPoint : byte;
 np : integer;
 OpenPolygon : boolean;
 XIntersection : real;
begin
 ToTheLeftofPoint := 0;
 ToTheRightofPoint := 0;
 OpenPolygon := False;
 if not ((TestPolygon[0].X = TestPolygon[High(TestPolygon)].X) and
   (TestPolygon[0].Y = TestPolygon[High(TestPolygon)].Y)) then
   OpenPolygon := True;
 for np := 1 to High(TestPolygon) do
   if ((TestPolygon[np - 1].Y <= P.Y) and
     (TestPolygon[np].Y > P.Y)) or
     ((TestPolygon[np - 1].Y > P.Y) and
     (TestPolygon[np].Y <= P.Y))
     then
   begin
     XIntersection := TestPolygon[np - 1].X +
       ((TestPolygon[np].X - TestPolygon[np - 1].X) /
       (TestPolygon[np].Y - TestPolygon[np - 1].Y)) * (P.Y - TestPolygon[np - 1].Y);
    if XIntersection < P.X then Inc(ToTheLeftofPoint);
     if XIntersection > P.X then Inc(ToTheRightofPoint);
   end;
 if OpenPolygon then
 begin
   np := High(TestPolygon);
   if ((TestPolygon[np].Y <= P.Y) and
     (TestPolygon[0].Y > P.Y)) or
     ((TestPolygon[np].Y > P.Y) and
     (TestPolygon[0].Y <= P.Y)) then
   begin
     XIntersection := TestPolygon[np].X +
       ((TestPolygon[0].X - TestPolygon[np].X) /
       (TestPolygon[0].Y - TestPolygon[np].Y)) * (P.Y - TestPolygon[np].Y);
     if XIntersection < P.X then Inc(ToTheLeftofPoint);
     if XIntersection > P.X then Inc(ToTheRightofPoint);
   end;
 end;
 if (ToTheLeftofPoint mod 2 = 1) and (ToTheRightofPoint mod 2 = 1) then Result := True
 else
   Result := False;
end;

procedure TformMain.Man;
var x,y: array [0..2] of TPoint;
   i,j: integer;
    p: PRGBArray;
begin
 b.Canvas.Brush.Color := clWhite;
 b.Canvas.FillRect(Rect(0, 0, b.Width, b.Height));

 x[0].X := 300;
 x[1].X := 300;
 x[2].X := b.Width-50;
 x[0].Y := 500;
 x[1].Y := 200;
 x[2].Y := 50;
 b.Canvas.Brush.Color := clYellow;
 b.Canvas.Polygon(x);

 y[0].X := 200;
 y[1].X := 300;
 y[2].X := b.Width - 50;
 y[0].Y := 550;
 y[1].Y := 250;
 y[2].Y := 100;
 b.Canvas.Brush.Color := clLime;
 b.Canvas.Polygon(y);

 b.TransparentColor := clwhite;
 b.Transparent := true;

 for j := 0 to b.Height-1 do
  begin
    p := b.scanline[j];
    for i:= 0 to b.Width-1 do
     begin
      if RGB(p[i].r, p[i].g, p[i].b) <> clWhite then
       if DotInRgn(x, Point(i,j)) and DotInRgn(y, Point(i,j)) then
        begin
         p[i].r := 128;
         p[i].g := 0;
         p[i].b := 0;
       end;
     end;
  end;

 Canvas.Draw(0, 0, b);
end;

procedure TformMain.FormPaint(Sender: TObject);
begin
 Man;
end;

procedure TformMain.FormResize(Sender: TObject);
begin
b.width := Clientwidth;
b.height := Clientheight;
Invalidate;
end;

procedure TformMain.FormCreate(Sender: TObject);
begin
 b := TBitMap.Create;
 b.pixelformat := pf24bit;
 b.width := Clientwidth;
 b.height := Clientheight;
 DoubleBuffered := True;
end;

procedure TformMain.FormDestroy(Sender: TObject);
begin
 b.Free;
end;

end.


Вроде бы нормальная скорость стала.



Страницы: 1 вся ветка

Форум: "Основная";
Текущий архив: 2007.02.25;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.48 MB
Время: 0.046 c
15-1170176379
Chort
2007-01-30 19:59
2007.02.25
Распределить текст по разным столбцам


15-1170225138
vitv
2007-01-31 09:32
2007.02.25
В чём преимущества MSSQL2000 над IB6X(FB1.5.X)?


2-1170936785
Darvin
2007-02-08 15:13
2007.02.25
Точное отслеживание времени с точностью 10 миллисекунд


2-1171021746
DenisNew
2007-02-09 14:49
2007.02.25
Параметры функций


2-1170362967
Pasha L
2007-02-01 23:49
2007.02.25
Считать буффер





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский