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

Вниз

И снова antialiasing   Найти похожие ветки 

 
Ал   (2006-03-04 15:49) [0]

Знатоки!

Пересмотрел все, что мог в Инете!
Нужен алгоритм рисования 2D полигона с антиалиасингом.
На http://www.codenet.ru/progr/video/antialiasing.php подробно описано словами. Но как запрограммировать - так и не понял!

Нужен работающий код. Если кому не жалко, помогите.

С уважением.


 
antonn ©   (2006-03-04 16:22) [1]

на лежит кнопка и TImage с картинкой bmp(!), по нажатию кнопки вызывается Button1Click. само рисование тоже в Button1Click. думаю, разберешься.

unit Unit1;

interface

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

type
 TForm1 = class(TForm)
   Image1: TImage;
   Button1: TButton;
   procedure Button1Click(Sender: TObject);
 private
   { Private declarations }
 public
   { Public declarations }
 end;

var
 Form1: TForm1;

implementation

{$R *.dfm}

procedure Alias(var SourceBitmap:TBitmap; CanvasOut:TCanvas; _R:TRect);
const
 MaxPixelCount = MaxInt div SizeOf(TRGBTriple);
type
 PRGBArray = ^TRGBArray;
 TRGBArray = array[0..MaxPixelCount-1] of TRGBTriple;
var
 x,y,cx,cy,cxi,totr,totg,totb,i: Integer;
 Row1,Row2,Row3,DestRow: PRGBArray;
begin
 for Y:=0 to (SourceBitmap.Height div 3)-1 do begin
   cy := y*3;
   DestRow := SourceBitmap.ScanLine[y];
   Row1:=SourceBitmap.ScanLine[cy];
   Row2:=SourceBitmap.ScanLine[cy+1];
   Row3:=SourceBitmap.ScanLine[cy+2];
  for x := 0 to (SourceBitmap.Width div 3)-1 do begin
     cx := x*3;
     totr := 0; totg := 0; totb := 0;
       for i := 0 to 2 do begin
         cxi := cx + i;
         totr := totr + Row1[cxi].rgbtRed + Row2[cxi].rgbtRed + Row3[cxi].rgbtRed;
         totg := totg + Row1[cxi].rgbtGreen + Row2[cxi].rgbtGreen + Row3[cxi].rgbtGreen;
         totb := totb + Row1[cxi].rgbtBlue + Row2[cxi].rgbtBlue + Row3[cxi].rgbtBlue;
       end;
       DestRow[x].rgbtRed := totr div 9;
       DestRow[x].rgbtGreen := totg div 9;
       DestRow[x].rgbtBlue := totb div 9;
   end;
  end;
 CanvasOut.CopyRect(_R,SourceBitmap.Canvas,rect(0,0,SourceBitmap.Width div 3,SourceBitmap.Height div 3));
end;

procedure BitmapPrepare(var SourceBitmap:Tbitmap; CanvasOut:TCanvas; _R:TRect);
begin
SourceBitmap.PixelFormat:=pf24bit;
SourceBitmap.Width:=(_r.Right-_r.Left)*3;
SourceBitmap.Height:=(_r.Bottom-_r.Top)*3;
SourceBitmap.Canvas.CopyRect(rect(0,0,SourceBitmap.Width,SourceBitmap.Height),Ca nvasOut,_R);
end;

procedure TForm1.Button1Click(Sender: TObject);
var _Bitmap:Tbitmap;
begin
_Bitmap:=TBitmap.Create;
 try

BitmapPrepare(_Bitmap,Image1.Picture.Bitmap.Canvas,rect(10,10,200,200)); //берем прямоугольник, в котором будет рисовать

//дальше работаем с _Bitmap.canvas как нам надо

_Bitmap.Canvas.Pen.Width:=3; //устанавливаем толщину в 3 раз больше

_Bitmap.Canvas.Ellipse(20*3,20*3,80*3,80*3);
_Bitmap.Canvas.MoveTo(50*3-1,60*3-1); //все координаты в 3 раза больше (хотя для лучшего эффекта, можно отнять еденицу - будет более смазано и качественно, главное не переборщить:))
_Bitmap.Canvas.LineTo(5*3,15*3);

_Bitmap.Canvas.Brush.Style:=bsclear;
_Bitmap.canvas.Font.Size:=_Bitmap.canvas.Font.Size*3; //тут правда косячно с размером...
_Bitmap.canvas.TextOut(2,2,"Im - super :)");

Alias(_Bitmap,Image1.Picture.Bitmap.Canvas,rect(10,10,200,200)); //вывод

 finally
_Bitmap.Free;
 end;
end;

end.


 
Ал   (2006-03-04 16:54) [2]

То есть используем доп. буфер, больший в 3 раза?

А можно ли прямым рисованием на битмапе с цветной текстурой, как в алгоритмах рисования линии, эллипса и т. п.?


 
antonn ©   (2006-03-04 17:30) [3]

Ал   (04.03.06 16:54) [2]
То есть используем доп. буфер, больший в 3 раза?

угу, можно и больше

> А можно ли прямым рисованием на битмапе с цветной
> текстурой, как в алгоритмах рисования линии, эллипса и
> т. п.?

не понял... ну в Image1 картинка, и на ней и рисуется все это дело


 
wicked ©   (2006-03-05 00:02) [4]

для Делфи есть такие варианты:
1) OpenGL - всем хорош, кроме того, что нужно заставить его рисовать в буффер в памяти.... таким свойством должна обладать, скажем, его программная реализация, но её все таки нужно умудриться включить.... это всё пишу "в теории", так как интересовался, но не делал.....
2) попробовать прикрутить что-то из того вала софта, который имеется на http://sf.net.... например, вот отсюда - http://vectorgraphics.sourceforge.net/ Недостаток - нужно искать библиотеки написанные на си (не си++) или делфи/паскале, сишные компилировать борландовским компилятором (лежит бесплатный у них на сайте), создавать модуль-обертку на делфи и линковать полученные .obj файлы..... при правильной постановке занятие это увлекательное и несложное, нужно только не забывать о соглашениях о вызове и паковании структур, буде таковые будут....
3) использовать GDI+ - там вроде есть такое... об этом хорошо у Джо (http://www.delphimaster.ru/cgi-bin/anketa.pl?id=1121389226) спросить - он делал что-то вроде....

из предложенного, думаю, оптимально будет попробовать эти пункты в обратном порядке - от 3-го к 1-му....
и не слушай никого, кто предложит Anti-Grain Geometry (http://antigrain.com) - хоть она и перекрывает GDI+ по качеству картинки, но писана она строго на си++ и к делфи её по-нормальному никак не прикрутить.... по ненормальному - писать на си++ готовые rendering pipelines, обеспечивать к ним процедурный интерфейс и помещать это дело в .dll....


 
antonn ©   (2006-03-05 07:18) [5]

wicked ©   (05.03.06 0:02) [4]
3) использовать GDI+ - там вроде есть такое... об этом хорошо у Джо (http://www.delphimaster.ru/cgi-bin/anketa.pl?id=1121389226) спросить - он делал что-то вроде....

там привязка идет к мегабайтной dll, под ХР она есть, под win2k по-умолчанию - нет. под win9x вообще не знаю, работает ли...


 
Ал   (2006-03-07 12:31) [6]

Спасибо всем за информацию!

Но хотелось бы что-нибудь более простое и не ресурсоемкое, вроде
http://alglib.sources.ru/graphics/

К сожалению, там нет полигона с заполнением.
Может, кто-нибудь подкинет полигон с заполнением, хотя бы без антиалиасинга. Дальше я бы сам попробовал.

С уважением.


 
Sapersky   (2006-03-07 15:05) [7]

http://www.g32.org/graphics32/index.html


 
DVM ©   (2006-03-12 23:02) [8]

Вот линия с антиалиазингом. Полигон можно сделать из линий.


TYPE
 TFColor  = record b,g,r:Byte end;
 PFColor  =^TFColor;

procedure SmoothLine(dc: HDC; x1, y1, x2, y2: Integer; c: TFColor);
var
 dx,dy,d,s,ci,ea,ec: Integer;
 p: tFColor;
begin
 if(y1=y2)or(x1=x2)then
 begin
   MoveToEx(dc, X1, Y1, nil);
   LineTo(dc, X2,y2);
 end
   else
 begin
   if y1>y2 then
   begin
     d:=y1; y1:=y2; y2:=d;
     d:=x1; x1:=x2; x2:=d;
   end;
   dx:=x2-x1;
   dy:=y2-y1;
   if dx>-1 then s:=1 else
   begin
     s:=-1;
     dx:=-dx;
   end;
   ec:=0;
   if dy>dx then
   begin
     ea:=(dx shl 16)div dy;
     while dy>1 do
     begin
       Dec(dy);
       d:=ec;
       Inc(ec,ea);
       ec:=ec and $FFFF;
       if ec<=d then Inc(x1,s);
       Inc(y1);
       ci:=ec shr 8;
       p.r:=GetRValue(GetPixel(DC,X1,Y1));
       p.g:=GetgValue(GetPixel(DC,X1,Y1));
       p.b:=GetbValue(GetPixel(DC,X1,Y1));
       p.b:=(p.b-c.b)*ci shr 8 + c.b;
       p.g:=(p.g-c.g)*ci shr 8 + c.g;
       p.r:=(p.r-c.r)*ci shr 8 + c.r;
       SetPixel(dc, x1, y1, Rgb(p.r, p.g, p.b));
       p.r:=GetRValue(GetPixel(DC,X1+s,Y1));
       p.g:=GetgValue(GetPixel(DC,X1+s,Y1));
       p.b:=GetbValue(GetPixel(DC,X1+s,Y1));
       p.b:=(c.b-p.b)*ci shr 8 + p.b;
       p.g:=(c.g-p.g)*ci shr 8 + p.g;
       p.r:=(c.r-p.r)*ci shr 8 + p.r;
       SetPixel(dc, x1+s, y1, Rgb(p.r, p.g, p.b));
     end;
   end else
   begin
     ea:=(dy shl 16)div dx;
     while dx>1 do
     begin
       Dec(dx);
       d:=ec;
       Inc(ec,ea);
       ec:=ec and $FFFF;
       if ec<=d then Inc(y1);
       Inc(x1,s);
       ci:=ec shr 8;
       p.r:=GetRValue(GetPixel(DC,X1,Y1));
       p.g:=GetgValue(GetPixel(DC,X1,Y1));
       p.b:=GetbValue(GetPixel(DC,X1,Y1));
       p.b:=(p.b-c.b)*ci shr 8 + c.b;
       p.g:=(p.g-c.g)*ci shr 8 + c.g;
       p.r:=(p.r-c.r)*ci shr 8 + c.r;
       SetPixel(dc, x1, y1, Rgb(p.r, p.g, p.b));
       p.r:=GetRValue(GetPixel(DC,X1,Y1+1));
       p.g:=GetgValue(GetPixel(DC,X1,Y1+1));
       p.b:=GetbValue(GetPixel(DC,X1,Y1+1));;
       p.b:=(c.b-p.b)*ci shr 8 + p.b;
       p.g:=(c.g-p.g)*ci shr 8 + p.g;
       p.r:=(c.r-p.r)*ci shr 8 + p.r;
       SetPixel(dc, x1, y1+1, Rgb(p.r, p.g, p.b));
     end;
   end;
 end;
end;



 
WondeRu ©   (2006-03-13 08:49) [9]

А GDI+ использовать религия не позволяет?



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

Форум: "Media";
Текущий архив: 2006.10.01;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.48 MB
Время: 0.024 c
2-1157374144
parovoZZ
2006-09-04 16:49
2006.10.01
Когда много панелей


15-1157986405
GRAND25
2006-09-11 18:53
2006.10.01
Какая замечательная статья!


15-1157806975
new_user1
2006-09-09 17:02
2006.10.01
Как узнать...


15-1157967587
Alex Bakulin
2006-09-11 13:39
2006.10.01
Автозапуск с Flash drive


1-1156155326
anton773
2006-08-21 14:15
2006.10.01
PrintDocument и PrintprevievDialog





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
Английский Французский Немецкий Итальянский Португальский Русский Испанский