Fast Canvas Library V1.052 lazarus / 39-Graphics ---------------------------------------------------------------------- Gigatron · 2025-06-09 16:01 Ok Here is the first release of my gfx Library V1.0 Include just base primitives to draw lines, rectangles , triangles , star, pixel(plot) etc. Will include the others functions in future release (copperbar, 2d,3d, Starfield, Image, plasma etc...) Step by Step ! This library is for my personal usage to make Demo faster Like on Amiga. It Use Winapi and working on my X64 windows. The performance is really faster. To start the show; Just start a new normal project and include a Timer... look the example code: Maybe i made mistakes and forgot some improvements ! Project is included. Have Fun Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, NativeFastCanvas,  Windows, ExtCtrls; type  { TForm1 }  TForm1 = class(TForm)    Timer1: TTimer;  procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private    FNativeFastCanvas: TNativeFastCanvas;    FAnimTimer: Integer;  public    procedure NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer); // Main Loop Draw  end; var  Form1: TForm1; implementation {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin  // Création du composant TNativeFastCanvas  FNativeFastCanvas := TNativeFastCanvas.Create(Self);   with FNativeFastCanvas do  begin    Parent := Self;    Align := alClient;         // Full Screen   // SetBounds(50,5,800,600); // or déclare screen size    BackgroundColor := RGB(0, 0, 32);  // Bleu foncé style Amiga    OnNativePaint := @NativeFastCanvas1NativePaint;  end;   FAnimTimer := 0;end; procedure TForm1.NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC;  Pixels: PFastPixel; Ww, Hh: Integer);var  FastCanvas: TNativeFastCanvas;  i, x, y: Integer;  CenterX, CenterY: Integer;  Radius: Integer;  Col: TColor;begin  FastCanvas := TNativeFastCanvas(Sender);  CenterX := Ww div 2;  CenterY := Hh div 2; // **** DÉMONSTRATION DES PRIMITIVES Dessin de BASE + Etoiles Triangle Etc .. *** // Stars  FastCanvas.Star(CenterX, CenterY, 30, 12, 5,  FAnimTimer * 0.02, RGB(255, 255, 0));  FastCanvas.Star(CenterX, CenterY, 60, 25, 5,  FAnimTimer * 0.03, RGB(255, 255, 0));  FastCanvas.Star(CenterX, CenterY, 100, 40, 5, FAnimTimer * 0.04, RGB(255, 255, 0));  FastCanvas.Star(CenterX, CenterY, 150, 60, 5, FAnimTimer * 0.01, RGB(255, 255, 0)); //  Pixels Random ! for i := 0 to 199 do // or 19999+1 pixels begin   x := Random(Ww);   y := Random(Hh);  // FastCanvas.SetPixel(x, y, RGB(255, 255, 255)); end;  // H Lines Copper bars style Amiga for i := 0 to 15 do  //16 lines begin   y := 50 + i * 4; // saut 4 pixel Y   Col := RGB(255 - i * 15, i * 16, 128 + i * 8);   FastCanvas.HorizontalLine(20, Ww - 20, y, Col); end;  // Vertical Lines for i := 0 to 20 do begin   x := 100 + i * 20;   FastCanvas.VerticalLine(x, 200, 280, RGB(0, 255, 100)); end;  // Diagonal Lines for i := 0 to 11 do begin   x := CenterX + Round(100 * Cos((i * 30 + FAnimTimer * 2) * Pi / 180));   y := CenterY + Round(100 * Sin((i * 30 + FAnimTimer * 2) * Pi / 180));   Col := RGB(255, 128 + i * 10, 0);   FastCanvas.Line(CenterX, CenterY, x, y, Col); end;  //  Rectangle The Big FastCanvas.Rectangle(10, 10, Ww - 10, Hh - 10,     RGB(255, 255, 255)); FastCanvas.Rectangle(10+1, 10+1, Ww - 9, Hh - 9, RGB(200, 200, 200));  // Rectangles Filled for i := 0 to 15 do begin   x := 50 + i * 50;   Col := RGB(i * 32, 255 - i * 32, 128);   FastCanvas.FillRect(x, Hh - 80, x + 40, Hh - 30, Col); end;  // Circle Radius := 80 + Round(20 * Sin(FAnimTimer * 0.1)); FastCanvas.Circle(CenterX - 150, CenterY, Radius, RGB(255, 0, 255));  // Circle Filled Radius := 60 + Round(10 * Sin(FAnimTimer * 0.15)); Col := RGB(255, 255 - Round(50 * Sin(FAnimTimer * 0.1)), 0); FastCanvas.FillCircle(CenterX + 150, CenterY, Radius, Col);  // Ellipse FastCanvas.Ellipse(CenterX, CenterY, 200, 120, RGB(0, 255, 255));  // Ellipse Filled x := CenterX + Round(180 * Cos(FAnimTimer * 0.05)); y := CenterY + Round(100 * Sin(FAnimTimer * 0.05)); FastCanvas.FillEllipse(x, y, 25, 15, RGB(0, 200, 100));  // Get Pixel then if not back color SetPixel mirror FX Col := FastCanvas.GetPixel(CenterX, CenterY); if Col <> RGB(0, 0, 32) then begin   FastCanvas.SetPixel(CenterX + 10, CenterY + 10, Col);   FastCanvas.SetPixel(CenterX - 10, CenterY - 10, Col); end;  // Simple Plasma Fx   100*100 for y := 320 to 420 do   for x := 20 to 120 do   begin     i := Round(128 + 127 * Sin((x + FAnimTimer) * 0.1) * Cos((y + FAnimTimer) * 0.08));     Col := RGB(i, 255 - i, 128);     FastCanvas.SetPixel(x, y, Col);   end; // Triangle animation  FastCanvas.Triangle(350, 450, 300, 350, 150, 450, RGB(255, 0, 0)); // Triangle animation  x := CenterX + Round(80 * Cos(FAnimTimer * 0.1));  y := CenterY + Round(80 * Sin(FAnimTimer * 0.1));  FastCanvas.Triangle(CenterX, CenterY - 60, x, y, CenterX - 40, CenterY + 40, RGB(0, 255, 0)); // Triangles  effet kaleidoscope fx  for i := 0 to 5 do    begin     x := CenterX + Round(100 * Cos(i * 60 * Pi / 180 + FAnimTimer * 0.05));     y := CenterY + Round(100 * Sin(i * 60 * Pi / 180 + FAnimTimer * 0.05));     Col := RGB(255, i * 40, 255 - i * 40);     FastCanvas.Triangle(CenterX, CenterY, x, y,       CenterX + Round(50 * Cos((i * 60 + 30) * Pi / 180 + FAnimTimer * 0.05)),       CenterY + Round(50 * Sin((i * 60 + 30) * Pi / 180 + FAnimTimer * 0.05)), Col);    end; end; procedure TForm1.Timer1Timer(Sender: TObject);begin  Inc(FAnimTimer);  FNativeFastCanvas.Invalidate;end; //  EXIT Destroy canvas !procedure TForm1.FormDestroy(Sender: TObject);begin  if Assigned(FNativeFastCanvas) then FNativeFastCanvas.Free;end; end. ---------------------------------------------------------------------- domasz · 2025-06-09 16:02 Splendid! ---------------------------------------------------------------------- 440bx · 2025-06-09 17:41 Hello Gigatron, I thought I'd have a look at your project.  When I tried to load it I got an error message about a missing package.  I looked in the OPM list and didn't see it there. The troublesome package is XMPlayer.  see attachment. My question is, how do I get that package installed so I can run your program ? ---------------------------------------------------------------------- Gigatron · 2025-06-09 19:41 Sorry, I forgot to remove the XMPlayer package; It is not yet in use, you can skip this component. Or install it for the future usage here ; https://forum.lazarus.freepascal.org/index.php/topic,71172.0.html ---------------------------------------------------------------------- Gigatron · 2025-06-09 22:15 Tired today with these vectors !! The next version of this library will contain filled triangle and vector text or Chars, as shown in this example image. ---------------------------------------------------------------------- Thaddy · 2025-06-10 05:24 How does it compare to OpenGLCanvas? ---------------------------------------------------------------------- Gigatron · 2025-06-10 18:05 Quote from: Thaddy on June 10, 2025, 07:24:09 amHow does it compare to OpenGLCanvas? OpenglCanvas is really faster than this library which is a little slower i think, but still fast according to the tests I performed. Let's upgrade this library to V1.01. Added filled triangles and vectorchar, vectorText, vector3drotate text etc... Future usage for loading and display png image , hope i'ts working for you. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i uses  Classes, SysUtils, Controls, Graphics, ExtCtrls, Windows, Types,  FPWritePNG, FPReadPNG, FPImage, IntfGraphics, GraphType;   List of Fuctions here : Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i     procedure HorizontalLine(x1, x2, y: Integer; Col: TColor);    procedure VerticalLine(x, y1, y2: Integer; Col: TColor);    procedure Line(x1, y1, x2, y2: Integer; Col: TColor);    procedure Rectangle(x1, y1, x2, y2: Integer; Col: TColor);    procedure FillRect(x1, y1, x2, y2: Integer; Col: TColor);    procedure Circle(CenterX, CenterY, Radius: Integer; Col: TColor);    procedure FillCircle(CenterX, CenterY, Radius: Integer; Col: TColor);    procedure Ellipse(CenterX, CenterY, RadiusX, RadiusY: Integer; Col: TColor);    procedure FillEllipse(CenterX, CenterY, RadiusX, RadiusY: Integer; Col: TColor);    procedure Triangle(x1, y1, x2, y2, x3, y3: Integer; Col: TColor);    procedure FillTriangle(x1, y1, x2, y2, x3, y3: Integer; Col: TColor);    procedure Star(CenterX, CenterY, OuterRadius, InnerRadius: Integer; Points: Integer; RotationAngle: Double; Col: TColor);    /// ****** END OF COMMON BASIC GFX PRIMITIVES ******************************     /// VectorChar Text Draw   ****************************    procedure DrawVectorChar(x, y: Integer; Ch: Char; Size: Integer; Col: TColor);    procedure DrawVectorText(x, y: Integer; const Txt: string; Size: Integer; Col: TColor);    procedure DrawVectorChar3D(x, y: Integer; Ch: Char; Size: Integer; RotX, RotY, RotZ: Single; Col: TColor);    procedure DrawVectorText3D(x, y: Integer; const Txt: string; Size: Integer; RotX, RotY, RotZ: Single; Col: TColor);    procedure RotateVectorText3D(GlobalX, GlobalY: Integer; Txt: string; Size: Integer; RotX, RotY, RotZ: Double; Col: TColor);  Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, NativeFastCanvas,  Windows, ExtCtrls; type  { TForm1 }  TForm1 = class(TForm)    Timer1: TTimer;  procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private    FNativeFastCanvas: TNativeFastCanvas;    FAnimTimer: Integer;  public    procedure NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer); // Main Loop Draw  end; var  Form1: TForm1;  RotX, RotY : Single; implementation {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin  // Création du composant TNativeFastCanvas  FNativeFastCanvas := TNativeFastCanvas.Create(Self);   with FNativeFastCanvas do  begin    Parent := Self;   // Align := alClient;         // Full Screen    SetBounds(30,5,960,620); // or déclare screen size    BackgroundColor := RGB(0, 0, 32);  // Bleu foncé style Amiga    OnNativePaint := @NativeFastCanvas1NativePaint;  end;   FAnimTimer := 0;  RotX := 0;  RotY := 0; end; procedure TForm1.NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC;  Pixels: PFastPixel; Ww, Hh: Integer);var  FastCanvas: TNativeFastCanvas;  i, x, y,x1,y1: Integer;  CenterX, CenterY: Integer;  Radius: Integer;  Col: TColor;begin  FastCanvas := TNativeFastCanvas(Sender);  CenterX := Ww div 2;  CenterY := Hh div 2;   // Triangles  effet kaleidoscope fx  for i := 0 to 5 do    begin     x := CenterX + Round(100 * Cos(i * 60 * Pi / 180 - FAnimTimer * 0.01));     y := CenterY + Round(100 * Sin(i * 60 * Pi / 180 - FAnimTimer * 0.01));     Col := RGB(i*50, i * 40, 255 - i * 40);     FastCanvas.FillTriangle(CenterX, CenterY, x, y,       CenterX + Round(150 * Cos((i * 60 + 30) * Pi / 180 - FAnimTimer * 0.02)),       CenterY + Round(150 * Sin((i * 60 + 30) * Pi / 180 - FAnimTimer * 0.02)), Col);    end;     rotY := FAnimTimer * 0.02;  rotX := FAnimTimer * 0.04;   FastCanvas.RotateVectorText3D(450, 520,'LAZARUS 4.0',70,0,  Roty, 0, RGB(255, 255, 255));  FastCanvas.RotateVectorText3D(450, 100,'GIGATRON',70,RotX,  RotY,0, RGB(255, 255, 255)); end; procedure TForm1.Timer1Timer(Sender: TObject);begin  Inc(FAnimTimer);  FNativeFastCanvas.Invalidate;end; //  EXIT Destroy canvas !procedure TForm1.FormDestroy(Sender: TObject);begin  // FNativeFastCanvas.FreeAllImages; // Libère toutes les images du cache // inherited Destroy;  if Assigned(FNativeFastCanvas) then FNativeFastCanvas.Free; end; end. ---------------------------------------------------------------------- Gigatron · 2025-06-11 21:41 Hi Status of this library 1.02; Include ; Normal Textscrolling, VectorTextScrolling, BitmapFontScrolling, Star with Border, Raster Bar , and Copper Bar V/H . Stay Tuned.. i will improve some functions. This Screen Size is 960x620 and all running on 60 fps !! Cpu load 2.5 - 3.0 % Some Gfx Operations is near opengl performance. Regards Gtr ---------------------------------------------------------------------- 440bx · 2025-06-11 22:03 @Gigatron, It looks great. Any chance you could post an updated project, with source please, that doesn't require an additional package ? Thank you. ---------------------------------------------------------------------- Gigatron · 2025-06-11 22:12 Quote from: 440bx on June 12, 2025, 12:03:32 am@Gigatron, It looks great. Any chance you could post an updated project, with source please, that doesn't require an additional package ? Thank you. Sure , i must just add some other stuff  like png image load / display, wavy texture , 2D/3D starfield, will improve some functions to gain maximum performance. The next release end of this week. ---------------------------------------------------------------------- 440bx · 2025-06-11 22:23 Quote from: Gigatron on June 12, 2025, 12:12:56 amSure , i must just add some other stuff  like png image load / display, wavy texture , 2D/3D starfield, will improve some functions to gain maximum performance. The next release end of this week. That sounds good.  Thank you!. ---------------------------------------------------------------------- Gigatron · 2025-06-12 16:44 Hi I did some tests and added some nice effects on this library, for example 15 fx running at full speed with 500000 dots, 3Dstarfield (pre-computed sin table), CPU load 15%. I'm going to clean up the code and add a plasma effect, so that's OK. Regards ---------------------------------------------------------------------- TBMan · 2025-06-13 12:38 Looks good! ---------------------------------------------------------------------- Gigatron · 2025-06-13 23:33 Quote from: TBMan on June 13, 2025, 02:38:56 pmLooks good! Thank you; Normally this library will be ready for Sunday, these are the compilations of all the effects i made with lazarus pascal similar to the Amiga demos. I can't include all the effects of the Amiga. I think there are millions of effects Some operations are really fast like pixel ops and draw gfx primitives ! Hope I didn't make any mistakes! An example demo (YT) of the latest version, you can see the performance of the various effects https://www.youtube.com/watch?v=9u5XQi5e23U Regards Gtr ---------------------------------------------------------------------- TBMan · 2025-06-14 01:26 Quote from: Gigatron on June 14, 2025, 01:33:39 amQuote from: TBMan on June 13, 2025, 02:38:56 pmLooks good! Thank you; Normally this library will be ready for Sunday, these are the compilations of all the effects i made with lazarus pascal similar to the Amiga demos. I can't include all the effects of the Amiga. I think there are millions of effects Some operations are really fast like pixel ops and draw gfx primitives ! Hope I didn't make any mistakes! An example demo (YT) of the latest version, you can see the performance of the various effects https://www.youtube.com/watch?v=9u5XQi5e23U Regards Gtr Very nice! Does it support page flipping? ---------------------------------------------------------------------- Gigatron · 2025-06-14 10:05 Hi Are you really need this image flip ? I think i have this effect in Javascript on my Storage HD; Maybe in future i can include this effect. Regards ---------------------------------------------------------------------- TBMan · 2025-06-14 16:29 Quote from: Gigatron on June 14, 2025, 12:05:36 pmHi Are you really need this image flip ? I think i have this effect in Javascript on my Storage HD; Maybe in future i can include this effect. Regards I use page flipping often with PTCGraph when doing games with constant animation going on. It does away with any flickering. Here's a demo of one of my games that uses page flipping. https://www.youtube.com/watch?v=q_EOf4jKW0c ---------------------------------------------------------------------- Gigatron · 2025-06-15 01:29 Ok Here is the FastCanvas Library 1.04 optimised with precalculated sin/cos tables. This library contain drawing pixels, and others effects to make some nice Amiga like demo intro. The included demo to show some functions in one line of code. So test it and send me feedback and bugs ! I will try to make doc of all functions in next days. Sometimes i have false positive virus alert in executable with functions. nfclibrary.zip include all you need to run the example. nfc=nativeFastCanvas Have Fun Gtr The minimal code to start projet with this library : Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, NativeFastCanvas,Windows, ExtCtrls; type  { TForm1 }  TForm1 = class(TForm)    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private    FNativeFastCanvas: TNativeFastCanvas;   public    procedure NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer);   end; var  Form1: TForm1; implementation {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin   FNativeFastCanvas := TNativeFastCanvas.Create(Self);  with FNativeFastCanvas do  begin    Parent := Self;    Align := alClient;    BackgroundColor := RGB(0, 0, 32);    OnNativePaint := @NativeFastCanvas1NativePaint;  end; end; procedure TForm1.NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC;Pixels: PFastPixel; Ww, Hh: Integer);var  FastCanvas: TNativeFastCanvas;begin  FastCanvas := TNativeFastCanvas(Sender);  FastCanvas.DC := DC;  FastCanvas.DrawVectorText(80, 100, 'HELLO LAZARUS 4.0', 35, RGB(255, 255, 0));end; procedure TForm1.Timer1Timer(Sender: TObject);begin  FNativeFastCanvas.Invalidate;end; procedure TForm1.FormDestroy(Sender: TObject);begin  if Assigned(FNativeFastCanvas) then FNativeFastCanvas.Free;end; end. ---------------------------------------------------------------------- 440bx · 2025-06-15 02:00 Quote from: Gigatron on June 15, 2025, 03:29:27 amThe included demo to show some functions in one line of code. So test it and send me feedback and bugs ! Very nice!  I just looked at the demo and, it is impressive.  I will spend some time studying your code as soon as I can (as usual, I'm in the middle of some code I need to "finish" someday). Thank you for sharing.  It will be very educational to study your code. ---------------------------------------------------------------------- Gigatron · 2025-06-17 00:30 Hi, For the next release V1.05  added some nice Fx; CopperBitmapScroller, Text fx, image reflection and more. Text from Megabyte inc Sinbad Cracktro.. talking about Amiga at 7.09MHZ !! Regards Gtr List of all commands of the FastCanvas Library V1.06 here : Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   **  Graphic Primitives *** Pixels and Bufferprocedure SetPixel(x, y: Integer; Col: TColor);function  GetPixel(x, y: Integer): TColor;procedure ClearBuffer(Col: TColor);procedure FastBlendPixel(x, y: Integer; Col: TColor; Alpha: Byte); *** Linesprocedure Line(x1, y1, x2, y2: Integer; Col: TColor);procedure HorizontalLine(x1, x2, y: Integer; Col: TColor);procedure VerticalLine(x, y1, y2: Integer; Col: TColor); *** Rectanglesprocedure Rectangle(x1, y1, x2, y2: Integer; Col: TColor);procedure FillRect(x1, y1, x2, y2: Integer; Col: TColor); *** Circles and Ellipsesprocedure Circle(CenterX, CenterY, Radius: Integer; Col: TColor);procedure FillCircle(CenterX, CenterY, Radius: Integer; Col: TColor);procedure CircleGradient(CenterX, CenterY, Radius: Integer; CenterCol, EdgeCol: TColor); procedure Ellipse(CenterX, CenterY, RadiusX, RadiusY: Integer; Col: TColor);procedure FillEllipse(CenterX, CenterY, RadiusX, RadiusY: Integer; Col: TColor);procedure EllipseGradient(CenterX, CenterY, RadiusX, RadiusY: Integer; CenterCol, EdgeCol: TColor); *** Trianglesprocedure Triangle(x1, y1, x2, y2, x3, y3: Integer; Col: TColor);procedure FillTriangle(x1, y1, x2, y2, x3, y3: Integer; Col: TColor); *** Starsprocedure Star(CenterX, CenterY, OuterRadius, InnerRadius: Integer;               Points: Integer; RotationAngle: Single; Col: TColor);procedure FillStar(CenterX, CenterY, OuterRadius, InnerRadius: Integer;                   Points: Integer; RotationAngle: Single; Col: TColor);procedure FillStarB(CenterX, CenterY, OuterRadius, InnerRadius: Integer;                    Points: Integer; RotationAngle: Single;                    FillCol: TColor; BorderCol: TColor; size: Integer); ** Vector Text *** 2D Textprocedure DrawVectorChar(x, y: Integer; Ch: Char; Size: Integer; Col: TColor);procedure DrawVectorText(x, y: Integer; const Txt: string; Size: Integer; Col: TColor); *** 3D Textprocedure DrawVectorChar3D(x, y: Integer; Ch: Char; Size: Integer;                          RotX, RotY, RotZ: Single; Col: TColor);procedure DrawVectorText3D(x, y: Integer; const Txt: string; Size: Integer;                          RotX, RotY, RotZ: Single; Col: TColor);procedure RotateVectorText3D(GlobalX, GlobalY: Integer; Txt: string; Size: Integer;                            RotX, RotY, RotZ: Single; Col: TColor); *** Scrolling Textprocedure VectorScrollingText(baseX, baseY: Integer; const txt: string;                             size: Integer; offset: Integer; col: TColor);procedure ScrollingText(baseX, baseY: Integer; const txt: string;                       FName: string; FSize: Integer; FStyle: TFontStyles;                       offset: Integer; col: TColor; charSpacing: Integer);procedure ScrollingTextSine(baseX, baseY: Integer; const txt: string;                         FName: string; FSize: Integer; FStyle: TFontStyles;                         offset: Integer; col: TColor; charSpacing: Integer;                           sineAmplitude: Integer; sineFrequency: Single; sinePhase: Single); **  Demoscene Effects *** Copper Bars and Raster Barsprocedure CopperBar(x1, y1, x2, y2: Integer; col1, col2, col3: TColor; vertical: Boolean);procedure CopperBarFill(x1, y1, x2, y2: Integer; col1, col2, col3: TColor;                     CopYsize, Offset: Integer);procedure RasterBar(x1, y1, x2, y2: Integer; col1, col2, col3: TColor);procedure AnimatedRasterBar(x1, y1, x2, y2: Integer; col1, col2, col3: TColor;                         offset: Integer); *** 2D Starfieldprocedure Init2DStarfield(starcount, direction: Integer; speed: Single;                       basecolor: TColor; screenWidth, screenHeight: Integer);procedure Update2DStarfield;procedure Render2DStarfield; *** 3D Starfieldprocedure Create3DStarfield(starCount: Integer; baseColor: TColor = clWhite;                           speed: Single = 1.0; rotationSpeed: Single = 0.01);procedure Update3DStarfield;procedure Render3DStarfield;procedure Set3DStarfieldColor(newColor: TColor);procedure Set3DStarfieldSpeed(NewSpeed: Single);procedure Set3DStarfieldRotation(NewRotationSpeed: Single);function Get3DStarfieldTotalCount: Integer; *** 2D BobFieldprocedure Create2DBobField(zoneX, zoneY, zoneX2, zoneY2, bobCount: Integer;                        imageFilename: string; direction: Integer;                        speed: Single; planeCount: Integer);procedure Update2DBobField;procedure Render2DBobField; *** 3D BobFieldprocedure Create3DBobField(bobCount: Integer; imageFilename: string;                        rotationSpeed: Single; speed: Single;                        minZ: Single = 10; maxZ: Single = 1000);procedure Update3DBobField;procedure Render3DBobField; *** Plasmaprocedure Plasma(x, y, ww, hh: Integer; time: Single);procedure PlasmaCustom(x, y, ww, hh: Integer; time: Single; col1, col2, col3: TColor); *** Chunky Copperprocedure ChunkyCopper(x, y, ww, hh, cellSize: Integer; angle, zoom: Single;                      const filename: string); ** Image Handling *** Loading and Cachefunction LoadImageToCache(const filename: string): Boolean;procedure FreeAllImages;procedure FreeOldestImage; *** Basic Displayprocedure DisplayImage(x, y: Integer; const filename: string;                      alpha: Byte = 255; scaleX: Single = 1.0; scaleY: Single = 1.0); *** Bitmap Font Scrollerfunction CreateBitmapFontScroller(fontFilename: string; scroll_Text: String;                                 charWidth, charHeight: Integer; offsetChar: Char;                                 sineHeight, scrollSpeed, startY, StartScrollPos: Integer): TBitmapFontScroller; **  Image Effects *** Wave Effectsprocedure DisplayImageWave(x, y: Integer; const filename: string;                        amplitude: Integer = 10; frequency: Single = 0.1;                        phase: Single = 0; transparency: TTransparencyMode = tmNone;                          transparentColor: TColor = clBlack); procedure DisplayImageWaveVertical(x, y: Integer; const filename: string;                                  amplitude: Integer = 10; frequency: Single = 0.1;                                  phase: Single = 0; transparency: TTransparencyMode = tmNone;                                transparentColor: TColor = clBlack); procedure DisplayImageWaveXY(x, y: Integer; const filename: string;                          amplitudeX: Integer = 10; frequencyX: Single = 0.1; phaseX: Single = 0;                            amplitudeY: Integer = 5; frequencyY: Single = 0.15; phaseY: Single = 0;                          transparency: TTransparencyMode = tmNone; transparentColor: TColor = clBlack); procedure DisplayImageWaveInterleaved(x, y: Integer; const filename: string;                                     amplitude: Integer = 10; frequency: Single = 0.1;                                   phase: Single = 0; transparency: TTransparencyMode = tmNone;                                     transparentColor: TColor = clBlack); *** Movement and Rotationprocedure ImageSineMove(const filename: string; baseX, baseY, amplitude: Integer;                     direction: Integer; phase: Single; scale: Single = 1.0; alpha: Byte = 255); procedure ImageSpinner(const filename: string; centerX, centerY: Integer;                      scale: Single; spinX, spinY: Single); *** Water Reflectionprocedure WaterReflection(x, y: Integer; const filename: string;                         waveAmplitude: Integer = 8; waveFrequency: Single = 0.15;                         time: Single = 0; reflectionAlpha: Byte = 180;                         reflectionHeight: Integer = -1); procedure WaterReflectionAdvanced(x, y: Integer; const filename: string;                                 time: Single = 0; reflectionAlpha: Byte = 160); **  Bitmap Text Effects *** Copper Bitmap Scrollprocedure CopperBitmapScroll(const fontFile: string; const txt: string;                            startX, y: Integer; charWidth, charHeight: Integer;                          offsetChar: Char; scrollSpeed: Integer; copperSpeed: Single;                          col1, col2, col3: TColor); procedure CopperBitmapScrollOptimized(const fontFile: string; const txt: string;                                     startX, y: Integer; charWidth, charHeight: Integer;                                     offsetChar: Char; scrollSpeed: Integer; copperSpeed: Single;                                   col1, col2, col3: TColor); *** Wave Text Effectsprocedure BitmapTextWave(  const fontFile: string;  const fullText: string;  baseX, baseY: Integer;  charWidth, charHeight: Integer;  offsetChar: Char;  charsPerLine: Integer;  time: Single;  waveAmplitude: Integer;  waveSpeed: Single = 1.0;  verticalWave: Boolean = True;  colorTint: Cardinal = $FFFFFF;  fadeAlpha: Byte = 255); procedure BitmapTextWaveCopper(  const fontFile: string;  const fullText: string;  baseX, baseY: Integer;  charWidth, charHeight: Integer;  offsetChar: Char;  charsPerLine: Integer;  time: Single;  waveAmplitude: Integer;  copperColor1, copperColor2, copperColor3: TColor;  copperSpeed: Single = 1.0;  copperDirection: Integer = 0;  copperHeight: Integer = 64;  waveSpeed: Single = 1.0;  verticalWave: Boolean = True;  lineSpacing: Integer = 0;  fadeAlpha: Byte = 255); *** Copper Scroll Controlsprocedure ResetCopperScroll;procedure SetCopperScrollPosition(position: Single);function GetCopperScrollPosition: Single; **  Typewriter System Create procedure CreateTypewriter(const txt: string; x, y, textSize: Integer;                          col: TColor; fontType: Integer; charDelayMs: Integer = 100;                          charsPerLine: Integer = 40; lineSpacing: Integer = 0;                          lineDelayMs: Integer = 300;                          const fontName: string = 'Arial'; fontStyle: TFontStyles = [];                        const bitmapFontFile: string = ''; offsetChar: Char = '0';                        bitmapCharWidth: Integer = 16; bitmapCharHeight: Integer = 16); ---------------------------------------------------------------------- Gigatron · 2025-06-19 23:47 Hi The Blitter Chip on Amiga was used memory block transfert faster than cpu 68000, Source, x,y,x1,y1 to x2,y2 The next version of native fast canvas include this chip simulator + all modern blend ops mode , exemple in attached picture ! Regards Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i //========= ====================================================================//             AMIGA BLITTER IMAGE-SOURCE,x1,y1,x2,y2,x3,y3,blitterMod//= ====================================================================== ======    procedure BlitCopy(const imageFile: string;                   srcX, srcY, srcW, srcH, destX, destY: Integer;                     mode: TBlitMode = bmCopy); overload;    procedure BlitCopy(const imageFile: string;                     srcRect: TBlitRect; destX, destY: Integer;                     mode: TBlitMode = bmCopy); overload;    procedure BlitCopyMasked(const imageFile, maskFile: string;                        srcX, srcY, srcW, srcH, destX, destY: Integer;                        mode: TBlitMode = bmCopy); ---------------------------------------------------------------------- Gigatron · 2025-06-21 17:07 Hi, I made a video of the upcoming version v1.05 of the FastCanvas library, including some cool Amiga style effects, I will release this version in a few days. Debugging takes a lot of time and it's not 100% stable. Precalculated Sintable extended to 36000 elements ! https://www.youtube.com/watch?v=w_Pj74K1jdk TypeWriter Demo : https://www.youtube.com/watch?v=w5E9ajtlm_0 1 line code for each writer : Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i 1: begin  FastCanvas.ImageReflection('tex/girl.png',50,200,RotZ,100,50.0);     F astCanvas.RotateBitmapText3D(CenterX,100,'TYPEWRITER','tex/038_64.png' ,64,64,' ',0,RotX,0,Rgb(0,200,255),64+4);     DrawStars(FastCanvas);    if (FAnimTimer mod (20*60)) = 0 then     begin          CurrentWriter := (CurrentWriter + 1) mod 3;           FastCanvas.FreeTypewriter;     end;        case CurrentWriter of        0: FastCanvas.TypewriterText(txt1, 700, 300, 50, RGB(100,200,255), tmVectorText,                                      60, 21, 60, 1000, '', [], '', ' ', 0, 0, True, 2);         1: FastCanvas.TypewriterText(txt2, 900, 300, 60, RGB(55,100,255), tmSystemText,                                      60, 21, 65, 1000, 'Arial', [fsBold], '', ' ', 0, 0, True, 2);         2: FastCanvas.TypewriterText(txt3, 900, 300, 40, RGB(0,255,0), tmBitmapText,                                      60, 21, 40, 1000, '', [], 'tex/040_32.png', ' ', 32, 32, True, 2);       end;      end;     Regards Gtr ---------------------------------------------------------------------- Gigatron · 2025-06-25 00:21 Ok This is the update release of nativefastCanvas of V1.051.. Removed some bugs and fixed stability, added some fx. Some parameters are changed in many commands then this version is not compatible with the old projects made with  v1.050 Send feedback and try it and good luck. Regards Gtr ---------------------------------------------------------------------- 440bx · 2025-06-25 01:57 Quote from: Gigatron on June 25, 2025, 02:21:59 amSome parameters are changed in many commands then this version is not compatible with the old projects made with  v1.5 Send feedback and try it and good luck. Regards Gtr Do you mean version 1.05 ?  Since you mention some parameters have changed causing incompatibilities with old projects, do you have plans to post 1 or 2 updated demos that use this new version ? Thank you! ---------------------------------------------------------------------- Gigatron · 2025-06-25 08:03 Quote from: 440bx on June 25, 2025, 03:57:32 amQuote from: Gigatron on June 25, 2025, 02:21:59 amSome parameters are changed in many commands then this version is not compatible with the old projects made with  v1.5 Send feedback and try it and good luck. Regards Gtr Do you mean version 1.05 ?  Since you mention some parameters have changed causing incompatibilities with old projects, do you have plans to post 1 or 2 updated demos that use this new version ? Thank you! Yes Sorry, I mean V1.050, and the next version will be 1.052 (maximum optimization for .png images for better management) and sure bug corrections !! Regards ---------------------------------------------------------------------- 440bx · 2025-06-25 10:11 Quote from: Gigatron on June 25, 2025, 10:03:24 amYes Sorry, I mean V1.050, and the next version will be 1.052 (maximum optimization for .png images for better management) and sure bug corrections !! Regards Thank you for clarifying that.  I thought it was most likely a typo but, wanted to be sure. ---------------------------------------------------------------------- Gigatron · 2025-06-26 00:35 Hi Quick made of Manic miner rooms (10) with this library; Project.zip and 2 sprite Sheet are included, sprites by Andy Nobles old manic miner remake on pc. code example : ** Edit Level 1 to 10 + Robot at Level1 , you can improve it Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, NativeFastCanvas,  Windows, ExtCtrls, StdCtrls; type  { TForm1 }  TForm1 = class(TForm)    Button1: TButton;    Button2: TButton;    Timer1: TTimer;     procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);    procedure ButtonPrevRoomClick(Sender: TObject);    procedure ButtonNextRoomClick(Sender: TObject);  private    FNativeFastCanvas: TNativeFastCanvas;   public    procedure NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer);   end; var  Form1: TForm1;  robotX : integer = 555;  robotY: integer = 255;  // Position actuelle  robotDirection: integer = 1;    // 1 = droite, -1 = gauche  robotSpeed: integer = 5;        // Vitesse  robotMinX: integer = 312;      // Distance limite gauche  robotMaxX: integer = 540;       // Distance limite droite    currentRoom: integer = 1;  roomNames: array[1..20] of String = (    'CENTRAL CAVERN','THE COLD ROOM','THE MENAGERIE','ABANDONED URANIUM WORKINGS',    'EUGENES LAIR','PROCESSING PLANT', 'THE VAT', 'MINER WILLY MEETS THE KONG BEAST',    'WACKY AMOEBATRONS','THE ENDORIAN FOREST','ATTACK OF THE MUTANT TELEPHONES',    'RETURN OF THE ALIEN KONG BEAST', 'ORE REFINERY','SKYLAB LANDING BAY',    'THE BANK','THE SIXTEENTH CAVERN','THE WAREHOUSE','AMOEBATRONS REVENGE',    'SOLAR POWER GENERATOR','THE FINAL BARRIER'  );  allRooms: array[1..10] of array[0..15] of string = (    // Room 1    (      '30000000090600006000000000000903',      '30000000000000009000000000000003',      '30000000000000000000000000000003',      '30000000000000000000000000000003',      '30000000000000000000000590050003',      '31111111111111444414444111111113',      '30000000000000000000000000000093',      '31110000000000000000000000000003',      '30000000000000000333050000000003',      '31111000777777777777777777770003',      '30000000000000000000000000000113',      '30000000000000000000000000000003',      '30000000000050000000333444441113',      '30000111111111111111000000000AB3',      '30000000000000000000000000000BB3',      '31111111111111111111111111111113'),    // Room 2    (      '30000000000000000003333333333333',      '30000000900000000000000090000063',      '30000000000000000000000000000003',      '30000000000000000000044410000003',      '30000000000000000000000000000003',      '31111111111111111111000000003003',      '30000000000000000000011113443003',      '31444440000000000000000003903003',      '30000000000000000000000003443003',      '30090000011111110000000003443003',      '30000000000000000004444003443003',      '300CCCC0000000000000000003443003',      '30000000000000111109000003443003',      '30000000444400000000000000000AB3',      '30000000000000000000000000000BB3',      '31111111111111111111111111111113'),      // Room 3    (      '30000090006000090020000900060003',      '30000000000000000060000000000003',      '30000000000000000000000000000003',      '30000000000000000000000000000003',      '30000000000000000000000000000003',      '31111444444444444444444444444443',      '30000000000000000000900000000093',      '31111110000000000000000000011113',      '32000000000000000000000000000003',      '32000077777700000000000000000003',      '32000000000000000000000001111113',      '36000000000000111110000000000AB3',      '30000111111000000000000000000BB3',      '30000000000000000000011111111113',      '30000000000000000000000000000003',      '31111111111111111111111111111113'),      // Room 4      (       '39000006000000333333333333333333',       '30000000000090000000000009000AB3',       '30000000000000000000000000000BB3',       '30000000000000000001111110000003',       '30000000000000000000000000011113',       '31000001000000000100000000000003',       '30000000000011009000011100000093',       '34440000000000000000000000000003',       '30000001100000000000000000111003',       '30000000000000000011100000000003',       '3CCC0000000000000000000000000013',       '30000000000011100000001110000003',       '30000011000000000000000600001113',       '30000000000000000011000000000003',       '30000000000000000000000000000003',       '31111111111111111111111111111113'),       // Room5       (       '30000000000000000000600000000003',       '30000000000000000000000000000093',       '30000000000000000000000000000003',       '30000000000000000000000000000003',       '30000000000000000000000050000003',       '31111111111111000044441111110003',       '30000000009000000000000000000113',       '30000000000000000000050000000903',       '30000000000000000077777777770003',       '30001111111111000000000000000003',       '30000000000000000000000000000003',       '34411111111111000011111110000013',       '30000009390000000000000000000003',       '311000003000003AB300000000000003',       '300005003000003BB333333355000003',       '31111111333333333333333311111113'),       // Room6       (       '30000000000000000000000000000AB3',       '30000000000000000000000000000BB3',       '30000000000000000000000000000003',       '30000000000000000000000000000003',       '30000000000000000000060000000003',       '30000000111000011000011111000003',       '30011000000000093900000000001113',       '30000000000000003000000000000093',       '30000000000000000000000111110003',       '31100000000000000000000000000003',       '39000001111111113111111111000003',       '30000000000009003600000000000003',       '30050000000000003000000000001113',       '30077770000000000000001100000003',       '30000000000000000000000000000003',       '31111111111111111111111111111113'),       // Room7       (       '30000000000000333333333333333333',       '30000000000000000000000000000003',       '30000000000000000000000000000003',       '30000000000000011344444444444493',       '30000000000000000344444444444443',       '30000007777700111344444444446443',       '31110000000000000344944444444443',       '30000000000000000344444444494443',       '31000000000000000344444644444443',       '30000000000000111344444444444443',       '31111111111100000349444444446443',       '30000000000000000344444444444493',       '30000000000000333344444644444443',       '300000000111003AB000000000000003',       '300000000000003BB000000000000003',       '31111111111111333333333333333333'),       // Room 8       (       '30600000006000000300300000000003',       '30000000000000000300300000000003',       '300000000000090EE300000000000113',       '30000000000000000300000000000003',       '30000000000000000300000000000003',       '31110000011111100311000000000003',       '30000000000000900300011110000013',       '30111000000000000300000000010003',       '30900000111000000300000000000003',       '30000000000000000311111000000003',       '31000000000011100300000000011113',       '30000000011000000D00000000000003',       '30001100000000000D00001111100003',       '30000000000CCC3AB311000000000903',       '300000000000003BB300000500000003',       '31111111111111111111111111111113'),       // Room 9      (        '3AB30000000000000000000000000003',        '3BB00000000000090000000000000003',        '30000000000000000000000000000003',        '30000000000000000000000000000003',        '30000000000000000000000000000003',        '31111001110011111111001110011003',        '30000000000000000000000000000003',        '30000000000000000000000000000113',        '300110011100CCCCCCCC000000000003',        '30000000000000000000001110011003',        '31100000000000000000000000000003',        '30000000000000000000000000000003',        '30011001110011111111001110011003',        '30000000000000000000000000000113',        '30000000000000000000000000000003',        '31111111111111111111111111111113'      ),      // Room 10      (    '30000000000601113060611111111113',      '30000000000000903000060000000093',      '31111110000000003000090000011113',      '30060000000000003000000000000003',      '30000000000000003111100000000003',      '30000000144444443000000111111113',      '31111000000900003000000000000003',      '30000000000000003111111144400003',      '31111100000000003090000000000003',      '36000000011111113000000000000113',      '31111440000000003111111100000063',      '30000000000000003000000644400003',      '30000000222222222200000000000003',      '311100000000AB000000000000001113',      '300000000000BB000000000000000003',      '22222222222222222222222222222222')     );  implementation function GetTile(x, y: integer): integer;var  ch: char;begin  if (x >= 0) and (x < 32) and (y >= 0) and (y < 32) and     (currentRoom >= 1) and (currentRoom <= 10) then    // 7 room  begin    ch := allRooms[currentRoom][y][x + 1];    case ch of      '0': Result := 0;      '1': Result := 1;      '2': Result := 2;      '3': Result := 3;    '4': Result := 4;      '5': Result := 5;      '6': Result := 6;    '7': Result := 7;      '9': Result := 9;      'A': Result := 10;  // case A      'C': Result := 12;      else Result := 11;  // empty    end;  end else    Result := 0;end; procedure UpdateRobot;begin  // Déplacer le robot  robotX := robotX + (robotDirection * robotSpeed);   if robotX <= robotMinX then    robotDirection := 1   // right walk  else if robotX >= robotMaxX then    robotDirection := -1; // leftend; {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin  FNativeFastCanvas := TNativeFastCanvas.Create(Self);  with FNativeFastCanvas do  begin    Parent := Self;    Align := alClient;    BackgroundColor := RGB(0, 0, 32);    OnNativePaint := @NativeFastCanvas1NativePaint;  end;end; procedure TForm1.NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC;Pixels: PFastPixel; Ww, Hh: Integer);var  FastCanvas: TNativeFastCanvas;  x, y, tileIndex, tileX, tileY: integer;  frameIndex: integer;begin  FastCanvas := TNativeFastCanvas(Sender);  FastCanvas.DC := DC;  FastCanvas.DrawVectorText(300, 560, roomNames[currentRoom], 25, RGB(255, 255, 255));   for y := 0 to 15 do  begin    for x := 0 to 31 do    begin      tileIndex := GetTile(x, y);       case tileIndex of        0..6: begin            // static sprites 32×32            tileX := (tileIndex mod 16) * 32;            tileY := ((currentRoom - 1) * 32) + (tileIndex div 16) * 32;           // if tileIndex > 0 then            Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;           7: begin // tapis          frameIndex := (GetTickCount div 150) mod 4; // 4 frames anim            tileX := 7*32 + frameIndex * 32;            tileY := ((currentRoom - 1) * 32);            Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;        12: begin // tapis            frameIndex := (GetTickCount div 150) mod 4; // 4 frames anim            tileX := 7*32 + frameIndex * 32;          tileY := ((currentRoom - 1) * 32);            Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;           9: begin // keys            frameIndex := (GetTickCount div 200) mod 4;            tileX := 352 + frameIndex * 32;            tileY := ((currentRoom - 1) * 32);          Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;          10: begin  // Case A - door 64×64 occupant 2×2 tiles           frameIndex := (GetTickCount div 500) mod 2;           tileX :=  ((currentRoom - 1) * 64);           tileY := 1344+(frameIndex * 64);           Fastcanvas.BlitCopy('64x64.png', tileX, tileY, 64, 64, 60+ x*32, 30+y*32, bmCopy);          end;       end;      end;   end;     frameIndex := (robotX div 16) mod 4;   if (currentRoom = 1) then  begin    if robotDirection = 1 then    begin      // right      tileX := 1024 + frameIndex * 72;      tileY := 0;    end    else    begin    // left      tileX := -22 + frameIndex * 72;      tileY := 64;    end;     Fastcanvas.BlitCopy('64x64.png', tileX, tileY, 64, 64, robotX, robotY, bmCopy);  end; end; procedure TForm1.Timer1Timer(Sender: TObject);begin  UpdateRobot;  FNativeFastCanvas.Invalidate;end; procedure TForm1.ButtonPrevRoomClick(Sender: TObject);begin  if currentRoom > 1 then  begin    currentRoom := currentRoom - 1;  end  else  begin    currentRoom := 10; // To room 10  end;  FNativeFastCanvas.Invalidate; // Redrawend; procedure TForm1.ButtonNextRoomClick(Sender: TObject);begin  if currentRoom < 10 then  begin    currentRoom := currentRoom + 1;  end  else  begin    currentRoom := 1; // To room 1  end;  FNativeFastCanvas.Invalidate; // Redrawend; procedure TForm1.FormDestroy(Sender: TObject);begin  if Assigned(FNativeFastCanvas) then FNativeFastCanvas.Free;end; end. ---------------------------------------------------------------------- Gigatron · 2025-06-26 16:56 Hi For manic miner if you want to go faster than light and see 1-20 level with less code use this code : load rooms.txt external data ; Replace the code above with this one. room.txt included Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, NativeFastCanvas,  Windows, ExtCtrls, StdCtrls; type  { TForm1 }  TForm1 = class(TForm)    Button1: TButton;    Button2: TButton;    Timer1: TTimer;     procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);    procedure ButtonPrevRoomClick(Sender: TObject);    procedure ButtonNextRoomClick(Sender: TObject);  private    FNativeFastCanvas: TNativeFastCanvas;   public    procedure NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer);   end; var  Form1: TForm1;  robotX : integer = 555;  robotY: integer = 255;          // Position actuelle  robotDirection: integer = 1;    // 1 = droite, -1 = gauche  robotSpeed: integer = 5;        // Vitesse  robotMinX: integer = 312;     // Distance limite gauche  robotMaxX: integer = 540;       // Distance limite droite   currentRoom: integer = 1;  maxRooms: integer = 0;   // Dynamique array for rooms and roomsNames  allRooms: array[1..20] of array[0..15] of string;  roomNames: array[1..20] of string;  implementation procedure LoadRoomsFromFile(const filename: string);var  fileLines: TStringList;  i, roomNum, lineNum: integer;  line: string;begin  fileLines := TStringList.Create;  try    fileLines.LoadFromFile(filename);     roomNum := 0;    lineNum := 0;     for i := 0 to fileLines.Count - 1 do    begin      line := Trim(fileLines[i]);       if (line = '') or (line[1] = '#') or (line[1] = '/') then        Continue;       if (Copy(line, 1, 4) = 'ROOM') or (Copy(line, 1, 4) = 'Room') then      begin        Inc(roomNum);        lineNum := 0;        if Pos(':', line) > 0 then        roomNames[roomNum] := Copy(line, Pos(':', line) + 1, Length(line))        else          roomNames[roomNum] := 'ROOM ' + IntToStr(roomNum);        Continue;      end;       if (roomNum > 0) and (lineNum < 16) and (Length(line) = 32) then      begin        allRooms[roomNum][lineNum] := line;        Inc(lineNum);      end;    end;     maxRooms := roomNum;   finally    fileLines.Free;  end;end; function GetTile(x, y: integer): integer;var  ch: char;begin  if (x >= 0) and (x < 32) and (y >= 0) and (y < 32) and     (currentRoom >= 1) and (currentRoom <= maxRooms) then  begin    ch := allRooms[currentRoom][y][x + 1];    case ch of      '0': Result := 0;      '1': Result := 1;      '2': Result := 2;      '3': Result := 3;    '4': Result := 4;      '5': Result := 5;      '6': Result := 6;    '7': Result := 7;      '9': Result := 9;      'A': Result := 10;      'C': Result := 12;      'D': Result := 13;      'E': Result := 14;    else Result := 20; // empty !!    end;  end else    Result := 20;end;  procedure UpdateRobot;begin  // Déplacer le robot  robotX := robotX + (robotDirection * robotSpeed);   if robotX <= robotMinX then    robotDirection := 1   // right walk  else if robotX >= robotMaxX then    robotDirection := -1; // leftend; {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin  FNativeFastCanvas := TNativeFastCanvas.Create(Self);  with FNativeFastCanvas do  begin    Parent := Self;    Align := alClient;  BackgroundColor := RGB(0, 0, 32);    OnNativePaint := @NativeFastCanvas1NativePaint;  end;   try    LoadRoomsFromFile('rooms.txt');  except    on E: Exception do    begin      ShowMessage('Erreur lors du chargement: ' + E.Message);    maxRooms := 1;      allRooms[1][0] := '31111111111111111111111111111113';    end;  end;  end; procedure TForm1.NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC;Pixels: PFastPixel; Ww, Hh: Integer);var  FastCanvas: TNativeFastCanvas;  x, y, tileIndex, tileX, tileY: integer;  frameIndex: integer;begin  FastCanvas := TNativeFastCanvas(Sender);  FastCanvas.DC := DC;  FastCanvas.DrawVectorText(100, 550, roomNames[currentRoom], 25, RGB(255, 255, 255));   for y := 0 to 15 do  begin    for x := 0 to 31 do    begin      tileIndex := GetTile(x, y);       case tileIndex of        0..6: begin            // static sprites 32×32            tileX := (tileIndex mod 16) * 32;            tileY := ((currentRoom - 1) * 32) + (tileIndex div 16) * 32;           // if tileIndex > 0 then            Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;           7: begin // tapis          frameIndex := (GetTickCount div 150) mod 4; // 4 frames anim            tileX := 7*32 + frameIndex * 32;            tileY := ((currentRoom - 1) * 32);            Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;        12: begin // tapis            frameIndex := (GetTickCount div 150) mod 4; // 4 frames anim            tileX := 7*32 + frameIndex * 32;          tileY := ((currentRoom - 1) * 32);            Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;           9: begin // keys            frameIndex := (GetTickCount div 200) mod 4;            tileX := 352 + frameIndex * 32;            tileY := ((currentRoom - 1) * 32);          Fastcanvas.BlitCopy('blocks.png', tileX, tileY, 32, 32, 60+x*32, 30+y*32, bmCopy);          end;          10: begin  // Case A - door 64×64 occupant 2×2 tiles           frameIndex := (GetTickCount div 500) mod 2;           tileX :=  ((currentRoom - 1) * 64);           tileY := 1344+(frameIndex * 64);           Fastcanvas.BlitCopy('64x64.png', tileX, tileY, 64, 64, 60+ x*32, 30+y*32, bmCopy);          end;       end;      end;   end;     frameIndex := (robotX div 16) mod 4;   if (currentRoom = 1) then  begin    if robotDirection = 1 then    begin      // right      tileX := 1024 + frameIndex * 72;      tileY := 0;    end    else    begin    // left      tileX := -22 + frameIndex * 72;      tileY := 64;    end;     Fastcanvas.BlitCopy('64x64.png', tileX, tileY, 64, 64, robotX, robotY, bmCopy);  end; end; procedure TForm1.Timer1Timer(Sender: TObject);begin  UpdateRobot;  FNativeFastCanvas.Invalidate;end; procedure TForm1.ButtonNextRoomClick(Sender: TObject);begin  if currentRoom < maxRooms then    currentRoom := currentRoom + 1  else    currentRoom := 1;  FNativeFastCanvas.Invalidate;end; procedure TForm1.ButtonPrevRoomClick(Sender: TObject);begin  if currentRoom > 1 then    currentRoom := currentRoom - 1  else    currentRoom := maxRooms;  FNativeFastCanvas.Invalidate;end; procedure TForm1.FormDestroy(Sender: TObject);begin  if Assigned(FNativeFastCanvas) then FNativeFastCanvas.Free;end; end. ---------------------------------------------------------------------- Gigatron · 2025-06-29 00:00 Hi, Maybe you would like to display more sprites on screen with the maximum performance if you want to make games or other nice work. The next version V1.052 include tilebatch to draw fast tiles 8x8,16x16 .. to 128x128 at max speed. For example the anim_stars.png contain 10 frames this portion of code display all the 10 frames with tiledbatch. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   StarsBatch: TTileBatch; implementation {$R *.lfm} procedure UpdateAndBatchStars(FastCanvas: TNativeFastCanvas; AnimTimer: Integer; ScrWidth, ScrHeight: Integer);var  i, j: Integer;  currentFrame: Integer;  animSpeed: Integer;  starSize: Integer;  starsRow, starsCol: Integer;  x, y: Integer;begin   StarsBatch.Count := 0;  animSpeed := 5;  starSize := 16*2;  starsRow := (ScrWidth div starSize) + 1;  starsCol := (ScrHeight div starSize) + 1;   for j := 0 to starsCol - 1 do  begin    for i := 0 to starsRow - 1 do    begin       if StarsBatch.Count >= High(StarsBatch.Tiles) then        Break;      x := i * starSize;      y := j * starSize;      currentFrame := ((AnimTimer + i * 2 + j * 3) div animSpeed) mod 10;       with StarsBatch.Tiles[StarsBatch.Count] do      begin        SrcX := currentFrame * 41;        SrcY := 0;        SrcW := 41;        SrcH := 37;        DestX := x;        DestY := y;        Alpha := 200 + Round(55 * Sin((AnimTimer + i + j) * 0.1));        Scale := 350 + Round(100 * Sin((i + j) * 0.3));      end;      Inc(StarsBatch.Count);    end;     if StarsBatch.Count >= High(StarsBatch.Tiles) then      Break;  end;   if StarsBatch.Count > 0 then FastCanvas.BlitTileBatch(StarsBatch);end;       Init on FormCreate the starsBatch counter and Image File Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.FormCreate(Sender: TObject);begin  FNativeFastCanvas := TNativeFastCanvas.Create(Self);  with FNativeFastCanvas do  begin    Parent := Self;    Align := alClient;    BackgroundColor := RGB(0, 0, 32);    OnNativePaint := @NativeFastCanvasPaint;  end;   StarsBatch.Count := 0;  StarsBatch.ImageFile := 'tex/anim_star.png'; UpdateAndBatchStars on Main loop of nfcpaint proc; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.NativeFastCanvasPaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer);   UpdateAndBatchStars(FastCanvas, FAnimTimer, Ww, Hh); ---------------------------------------------------------------------- Gigatron · 2025-07-07 16:45 Hi, Very busy yet , here is the state of the next versipn V1.052; (Fixed some bugs) Stars, StarsB and others. ImageMoveTo(x,y, to x1,to y1) with Easeing ; Tweens; Image Skew X/Y ImagePerspective .. and so. Here is a little video demonstrate Easing and Tweens system.. This library will released soon .. when bugs fixed. Regards https://www.youtube.com/watch?v=RE-YtJdnKYA ---------------------------------------------------------------------- Lulu · 2025-07-07 17:58 the effects are nice ---------------------------------------------------------------------- RAW · 2025-07-11 21:49 There is also FastDIB or back in the days (D5) there was FastLIB (I guess WinAPI DIB + 32bit ASM). Maybe people who like FastCanvasLIB are interested in things like that too.... Maybe there is more stuff out there in this category.. ---------------------------------------------------------------------- Gigatron · 2025-07-12 12:49 Quote from: RAW on July 11, 2025, 11:49:38 pmThere is also FastDIB or back in the days (D5) there was FastLIB (I guess WinAPI DIB + 32bit ASM). Maybe people who like FastCanvasLIB are interested in things like that too.... Maybe there is more stuff out there in this category.. Sure the same style, but this library is for oldschool demo effects Here is the version 1.052 bugs are fixed hope so ! The library is included in the project.zip ; and a demo of barnsley's Fern Leaf based on Boleeman example; Regards ---------------------------------------------------------------------- Gigatron · 2025-07-14 11:47 Hi Now it's time to use this library for making demo now ! 3D wireFrame Sphere in action; https://www.youtube.com/watch?v=UE3EegXD0i4 // Sorry it's not Cube but Sphere, Cube is another project project.zip is atached ; When you Start project with this library use the following code. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, NativeFastCanvas,Windows, ExtCtrls; type  { TForm1 }  TForm1 = class(TForm)    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private    FastCanvas: TNativeFastCanvas;   public    procedure NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC; Pixels: PFastPixel; Ww, Hh: Integer);   end; var  Form1: TForm1; implementation {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin   FastCanvas := TNativeFastCanvas.Create(Self);  with FastCanvas do  begin    Parent := Self;    Align := alClient;    BackgroundColor := RGB(0, 0, 32);  OnNativePaint := @NativeFastCanvas1NativePaint;  end; end; procedure TForm1.NativeFastCanvas1NativePaint(Sender: TObject; DC: HDC;Pixels: PFastPixel; Ww, Hh: Integer);begin   FastCanvas.DC := DC;  FastCanvas.DrawVectorText(80, 100, 'HELLO LAZARUS 4.0', 35, RGB(255, 255, 0));end; procedure TForm1.Timer1Timer(Sender: TObject);begin  FastCanvas.Invalidate;end; procedure TForm1.FormDestroy(Sender: TObject);begin  if Assigned(FastCanvas) then FastCanvas.Free;end; end. ---------------------------------------------------------------------- Gigatron · 2025-07-20 00:39 Hi A more complex library is glCanvas in beta version using TOpenGLControl; Some functions are not working yet but a nice demo is Ok ! All files are atached to run this demo; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls,OpenGLContext,  glCanvas, gl,Math; type  { TForm1 }  TForm1 = class(TForm)    Timer1: TTimer;  OpenGLControl1: TOpenGLControl;    procedure FormCreate(Sender: TObject);    procedure Timer1Timer(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);  private    FTime: Single;    FStars: array[0..99999] of TStar;    Ftex: GLuint;     procedure InitStarfield;    procedure UpdateStarfield;  public  end; var  Form1: TForm1; implementation {$R *.lfm} { TForm1 } procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  if not OpenGLControl1.MakeCurrent then    raise Exception.Create('Impossible de faire current OpenGL context.');  FTime := 0;    Ftex := LoadPNGToTexture('girl4.png');  InitStarfield; end; procedure TForm1.InitStarfield;var  i: Integer;begin  for i := 0 to High(FStars) do  begin    FStars[i].x := (Random - 0.5) * 200;    FStars[i].y := (Random - 0.5) * 200;    FStars[i].z := Random * 10 + 0.1;    FStars[i].brightness := Random + 3.5;  end;end; procedure TForm1.UpdateStarfield;var  i: Integer;begin  for i := 0 to High(FStars) do  begin    FStars[i].z := FStars[i].z - 0.02;    if FStars[i].z <= 0 then    begin      FStars[i].x := (Random - 0.5) * 200;      FStars[i].y := (Random - 0.5) * 200;      FStars[i].z := 10;      FStars[i].brightness := Random + 3.5;    end;  end;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  FTime := FTime + 0.008;  UpdateStarfield;  OpenGLControl1.Invalidate;end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  i: Integer;  centerX, centerY: Single;  color1: TglColor;  offsetX, offsetY: Single;    r, g, b: Single;const  MinVal = 0.1; begin  if not OpenGLControl1.MakeCurrent then Exit;   centerX := OpenGLControl1.Width / 2;  centerY := OpenGLControl1.Height / 2;   glFillScreen(OpenGLControl1, 0.1, 0.1, 0.2, 1.0);   offsetX := Sin(FTime * 4) * 300;  // oscillation horizontale  offsetY := Cos(FTime * 3) * 30;  r := Abs(sin(FTime * 1.1)) * (1 - MinVal) + MinVal; // entre 0.1 et 1.0  g := Abs(sin(FTime * 1.3 + 2)) * (1 - MinVal) + MinVal;  b := Abs(sin(FTime * 1.7 + 4)) * (1 - MinVal) + MinVal;   glDrawTexture(centerX-100 + offsetX, centerY - 100 ,              256, 256, Ftex,                4.0, 4.0,                0,              r,g,b,                1.0);   glStarfield(FStars, 0.1, OpenGLControl1.Width, OpenGLControl1.Height);   for i := 0 to 17 do  begin    color1 := glColorHSV((FTime * 60 + i * 72) mod 360, 1, 1, 0.8);    glCircle(      centerX + cos(FTime + i * 0.35) * 400,      centerY + sin(FTime + i * 0.35) * 400,      40 + sin(FTime * 3)*10,    15,      color1.r, color1.g, color1.b, color1.a,      True    );    glCircle(      centerX + cos(-FTime + i * 0.35) * 300,      centerY + sin(-FTime + i * 0.35) * 300,      40 + sin(FTime * 3)*10,      15,    color1.r, color1.g, color1.b, color1.a,      True    );    end;   glRect(centerX - 100, centerY - 100, 200, 200, 1, 0, 0, 0.5, False, 4);   color1 := glColorHSV((FTime * 120) mod 360, 1, 1, 1);  glStar(centerX, centerY, 160, 5, FTime * 90, color1.r, color1.g, color1.b, color1.a, False, 6);  glStar(centerX, centerY, 80, 8,  -FTime * 90, color1.r, color1.g, color1.b, color1.a, False, 4);   for i := 0 to 2 do  begin    color1 := glColorHSV((FTime * 90 + i * 120) mod 360, 1, 1, 0.7);    glTriangle(      centerX + cos(FTime * 0.5 + i * 2.094) * 300,      centerY + sin(FTime * 0.5 + i * 2.094) * 300,    30,  // taille 15 -> 30      FTime * 180,      color1.r, color1.g, color1.b, color1.a,      True    );  end;   for i := 0 to 7 do  begin    color1 := glColorHSV((FTime * 60 + i * 90) mod 360, 1, 1, 0.4);    glCircle(centerX, centerY, 120 + i * 50 + sin(FTime * 2) * 60, 6+(i*8),             color1.r, color1.g, color1.b, color1.a, False, 1+i*2);  end;   for i := 0 to 7 do  begin    color1 := glColorHSV((FTime * 180 + i * 45) mod 360, 1, 1, 0.6);    glLine(    centerX,      centerY,      centerX + cos(FTime + i * 0.785) * 800,    centerY + sin(FTime + i * 0.785) * 800,      color1.r, color1.g, color1.b, color1.a,      10 );  end;   OpenGLControl1.SwapBuffers;end; end. ---------------------------------------------------------------------- Gigatron · 2025-07-25 21:52 Hi Here is the next version of the Glcanvas v0.32 you can add glsl pixel shader ;  and a nice shader fx; If you have not Amstrad CPC464 font replace it by Arial or some other font. Have fun; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls, StdCtrls,  OpenGLContext, glCanvas,gl; type   { TForm1 }  TForm1 = class(TForm)    Memo1: TMemo;    Memo2: TMemo;    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure Timer1Timer(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);  private    Stime: Single;    Laztex, Shader1Tex, Shader2Tex: GLuint;   public  end; var  Form1: TForm1;  scx : integer;  FragmentShader1 :Pchar;  FragmentShader2 :Pchar;// texte sinus implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  if not OpenGLControl1.MakeCurrent then    raise Exception.Create('OpenGL context makeCurrent Error');  STime := 1.0;  scx := 0;  Laztex := LoadPNGToTexture('tex/g5.png');  FragmentShader1 := Pchar(Memo1.Text);  FragmentShader2 := Pchar(Memo2.Text);   Shader1Tex := glMakeShaderProgram('', FragmentShader1);  if Shader1Tex = 0 then raise Exception.Create('Échec de compilation du shader');   Shader2Tex := glMakeShaderProgram('', FragmentShader2);  if Shader2Tex = 0 then raise Exception.Create('Échec de compilation du shader');  end; procedure TForm1.Timer1Timer(Sender: TObject);begin  STime += 0.16;  scx  := (scx+10) mod 9000;     // reset after 9000  OpenGLControl1.Invalidate;end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var i : integer;   copperCol1, copperCol2, copperCol3: TglColor;begin if not OpenGLControl1.MakeCurrent then Exit;     glFillScreen(OpenGLControl1, 0.0, 0.3, 0.6, 1.0);    copperCol1  := glColorRGBA(0.0, 0.0, 0.0, 1.0);   copperCol2  := glColorRGBA(1.0, 1.0, 1.0, 1.0);   copperCol3  := glColorRGBA(0.0, 0.0, 0.0, 1.0);    glCopperBarFill(0, -64, 1980, 256*5, copperCol1, copperCol2, copperCol3, 64, Stime*5);    glDrawShaderText(1980-scx, 700, UpperCase(' ... Hello Shader ! This Is The New GL Canvas Gigatron 2025 ... ... Hello Shader ! This Is The New GL Canvas Gigatron 2025 ...'),               'Amstrad CPC464', 32, [fsBold], 0.0, 1.0, 0.0, 1.0, Shader2Tex, Stime/3.0);    if (Laztex <> 0) and (Shader1Tex <> 0) then      glDrawTexturedShader(450, 0, 1024, 1024, Laztex, Shader1Tex, 1, 1, 1, 0.8, Stime/5.0);    OpenGLControl1.SwapBuffers;end; procedure TForm1.FormDestroy(Sender: TObject);begin  if Shader1Tex <> 0 then glDeleteTextures(1, @Shader1Tex);  if Shader2Tex <> 0 then glDeleteTextures(1, @Shader2Tex);end; end. ---------------------------------------------------------------------- Gigatron · 2025-08-01 22:20 Hi Another version of glCanvas v0.034 with 80 rotating cubes + rainbow text shader, With minimal code except fragment shader on Memo1 text; Regards Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls, StdCtrls,  Spin, OpenGLContext, glcanvas, gl; type  { TForm1 }  TForm1 = class(TForm)    FloatSpinEdit1: TFloatSpinEdit;    Memo1: TMemo;    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private    rot: Single;    Txt_Shader: GLuint;  public  end; var  Form1: TForm1;  Txt_Fragment :Pchar;  txt : string =' GL CUBE DEMO GIGATRON 2025 '; implementation {$R *.lfm} { TForm1 } procedure TForm1.Timer1Timer(Sender: TObject);begin  OpenGLControl1.Invalidate;end; procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1); // need  if not OpenGLControl1.MakeCurrent then raise Exception.Create('OpenGL context makeCurrent Error');  rot := 0;  Txt_Fragment := Pchar(Memo1.Text);  Txt_Shader := glMakeShaderProgram('', Txt_Fragment);  if Txt_Shader = 0 then raise Exception.Create('Échec de compilation du shader');end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  i, j: Integer;begin  if not OpenGLControl1.MakeCurrent then Exit; // need  glFillScreen(OpenGLControl1, 0.0, 0.0, 0.0, 1.0); // need   for i:=0 to 9 do   for j:=0 to 7 do   glFilled3DCube(OpenGLControl1, -80 +i*18, 75-j*18, 0,  10,  // x=3D Screen Spece 0= center                               0 + round(j*36)/255, 1.0-round(j*64)/255, 0 +(round(i*28*2)/255) , 1.0,                             rot, -rot, -rot, 0.0, 0.0, 1.0);  // 2D  glSetUniformFloat(Txt_Shader,'frequency',FloatSpinEdit1.Value); // uniform float; memo1 frag shader  glDrawShaderText(400, 800, txt,'Arial', 42, [fsBold], 1.0, 1.0, 1.0, 1.0, Txt_Shader, rot/50);   rot += 2.60;   OpenGLControl1.SwapBuffers; // needend; end. ---------------------------------------------------------------------- Gigatron · 2025-08-02 20:15 Hi Here is the next version of glCanvas V0.036 with 3d Primitives. Online YT demo : https://www.youtube.com/watch?v=IJ6gB9_uwdU See you ; ---------------------------------------------------------------------- Gigatron · 2025-08-05 22:19 Hi Added some nice functions to Gl Canvas V0.037 and finished the demo. This library is near 95 % usable and will be uploaded soon, if some 3D perspective corrections and minor bugs fixed . Online demo on YT : https://www.youtube.com/watch?v=RyXYP-4H-jk Regards ---------------------------------------------------------------------- ADMGNS · 2025-08-08 00:59 hello good work.. and thanks a lot.. what about native support for other platforms, ie Linux support, maybe at next versions?? regs ---------------------------------------------------------------------- Gigatron · 2025-08-08 12:06 Quote from: ADMGNS on August 08, 2025, 02:59:01 amhello good work.. and thanks a lot.. what about native support for other platforms, ie Linux support, maybe at next versions?? regs Hi I don't have Linux, you'd have to try it out but i think it should work, at least for some gl commands from the glCanvas library so it's worth checking. Regards ---------------------------------------------------------------------- Gigatron · 2025-08-08 12:52 Hi again Finally here is the V0.037 with a lot of GL commands plus a nice demo with individual star rotation plus space rotation. I hope I didn't make any mistakes.. Use this library with caution even though I corrected quite a few errors. I don't want to be responsible for any data loss or other problems related to your computer. So be careful. Attachements : project1.zip with glcanvas V 0.037 + 3D Sprite Starfield : Left & Right key to Rotate 2D Space star.png ---------------------------------------------------------------------- Gigatron · 2025-08-08 18:43 Hi, A little demo to starting use glcanvas. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls, OpenGLContext, glcanvas, Gl; type  { TForm1 }  TForm1 = class(TForm)   OpenGLControl1: TOpenGLControl;   Timer1: TTimer;   procedure FormCreate(Sender: TObject);   procedure OpenGLControl1Paint(Sender: TObject);   procedure Timer1Timer(Sender: TObject); private   tmr: Single; public end; var Form1: TForm1; implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin glInit(OpenGLControl1);end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var i : integer;begin  glFillScreen(OpenGLControl1, 0,0,0, 1.0); // Need   for i:=0 to 10 do  glCircle(350 + i *110 , 100,    50   ,     3+i*2      ,  1.0, 1.0, 1.0, 0.7, True);  //        X           , Y           ,  Radius,   Segments   ,  color RGBA        ,Filled ?   glLine(400, 200, 600, 250, 1.0, 0.0, 0.0, 1.0, 3.0);  glLine3D(1200, 600, 0, 1400, 700, 0, 0.9, 0.1, 0.9, 1.0, 4.0);   glRect(700, 200, 180, 100,     glColorRGBA(0.0, 1.0, 0.0, 1.0), False, 2.5);  glRectFast(900, 200, 180, 100, glColorRGBA(0.0, 0.4, 1.0, 0.8));   glCircle(500, 400, 70, 40, 1.0, 0.2, 1.0, 1.0, False, 2.5);  glCircle(700, 400, 70, 40, 0.0, 1.0, 1.0, 0.7, True);   glTriangle(900, 400, 90,   tmr, 1.0, 1.0, 0.0, 1.0, False, 2.5);  glTriangle(1100, 400, 90, -tmr, 1.0, 0.5, 0.0, 0.8, True);   glEllipse(500, 600, 100, 60, 40, 1.0, 0.7, 0.8, 1.0, False, 2.5);  glEllipse(700, 600, 100, 60, 40, 0.8, 0.3, 0.9, 0.7, True);   glStar(900, 600, 60, 5, tmr*2, 1.0, 0.8, 0.0, 1.0, False, 2.5);  glStar(1100, 600, 50, 8, -tmr, 0.8, 0.2, 0.2, 0.9, True);   glStar(900,  800, 80, 10, 18+tmr *  1.0, 0.6, 0.6, 0.6, 1.0, True);  glStar(1020, 800, 80, 10, -tmr * 1.0, 0.8, 0.9, 0.8, 1.0, True);   glQuad(1200, 200, 1350, 180, 1380, 300, 1230, 320, 0.6, 0.2, 0.8, 1.0, True);  glQuad(1200, 400, 1350, 380, 1380, 500, 1230, 520, glColorRGBA(0.9, 0.2, 0.8, 1.0), True);   OpenGLControl1.SwapBuffers; // Need !end; procedure TForm1.Timer1Timer(Sender: TObject);begin tmr := tmr + 1.5; if tmr > 360.0 then tmr := tmr - 360.0; OpenGLControl1.Invalidate;end;end. ---------------------------------------------------------------------- ADMGNS · 2025-08-08 18:47 hi again yesterday i,d tried fastCanvas, but it was based on Windows graphis, ie DC. it doesnt work/compile on Linux as expected. now, i,ve tried glCanvas, yes, it works: galaxy effect let it easy.. ---------------------------------------------------------------------- Gigatron · 2025-08-11 00:44 Hi Let's continue to make some interesting drawing with glcanvas 0.038. Pseudo 3D based on Lou's Page to draw Out-Run Road from .js Code. I included some function in glcanvas to reduce the code. Base source : http://www.extentofthejam.com/pseudo/ Code and library in project1.zip Have fun ---------------------------------------------------------------------- Gigatron · 2025-08-12 22:36 Hi Now let's try to add road with curves. glcanvas lib updated to v0.039 ! Regards ---------------------------------------------------------------------- Lulu · 2025-08-13 18:19 I like that! I always wondered how they managed to do that. Thanks to share ---------------------------------------------------------------------- Gigatron · 2025-08-13 23:19 Quote from: Lulu on August 13, 2025, 08:19:12 pmI like that! I always wondered how they managed to do that. Thanks to share  Your are welcome @Lulu. So missing Hills... are added. Regards ---------------------------------------------------------------------- Gigatron · 2025-08-16 23:59 Hi Demo with the new glCanvas V0.040 ... some functions are renamed !! gldraw2Dtexture with all variations; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure glDrawTexture2D(x, y, w, h: GLfloat; texID: GLuint;                      scaleX: GLfloat = 1.0; scaleY: GLfloat = 1.0;                      rotation: GLfloat = 0.0;                        red: GLfloat = 1.0;                        green: GLfloat = 1.0;                        blue: GLfloat = 1.0;                        alpha: GLfloat = 1.0;                      FlipX: Boolean = False;                        FlipY: Boolean = False); Have Fun , ---------------------------------------------------------------------- Gigatron · 2025-08-18 10:56 Hi Shadow of the beast is a fantastic game on Amiga 500.. I tried to make a parallax scrolling of level 1(the plain) (50%)  using Vsync command of the glCanvas library V0.041 to obtain a smooth scrolling like blitter on Amiga. The code is very very basic and easy to understand. glInit(OpenGLControl1); glEnableVSync(true); // vsync + Procedure Application.onIdle (Mainloop) without Timer. The gfx are from Titan Shadow Of the beast Page, so try it use left + right arrow to scroll ! https://www.magnodyne.com/Fichiers/sites/sotb/index_fr.html Project1.zip , sotb.zip(sprites) Regards ---------------------------------------------------------------------- Gigatron · 2025-08-21 00:44 Hi I am not clever than Sega Coders but played with outrun road to make Space harrier floor. Use L/R/U/D arrows to scroll the screen. Have Fun ---------------------------------------------------------------------- Gigatron · 2025-08-21 15:46 Hi Today i've tested Vsync to stabilize FPS with 10000 sprites, i've got 30FPS with my LabTop PC. In addition we can load png,jpg textures with glcanvas. I would like to share the code with you. Regards GTR ---------------------------------------------------------------------- Gigatron · 2025-08-22 15:43 Hi A nice command of glcanvas is glBlitCopy to copy a part of texture to destinationx, y. Here is a demonstration of this command to make a texture wobble fx, for that we need sintable contains all X position of each part of logo. So see the code and example project. Regards Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls,  OpenGLContext, glcanvas, gl, Math; type   { TForm1 }  TForm1 = class(TForm)    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end; var  Form1: TForm1;  laz_tex: GLuint;  sintable: array of Integer; // dynamic sintable array !  table_index, logo_w, logo_h : Integer; implementation {$R *.lfm} procedure sinus(amplitude, nb_steps, nb_cycles: Integer);var  totalSteps, i: Integer;  step, a: Single;  value: Integer;begin  totalSteps := nb_steps * nb_cycles;  step := (2 * Pi) / nb_steps;  SetLength(sintable, Length(sintable) + totalSteps);  for i := 0 to totalSteps - 1 do  begin    a := i * step;    value := Round(amplitude * Sin(a));    sintable[High(sintable) - totalSteps + 1 + i] := value;  end;end; procedure stay(nbTimes: Integer); // number of time to Fill sintable with '0'var  i, len: Integer;begin  len := Length(sintable);  SetLength(sintable, len + nbTimes);  for i := 0 to nbTimes - 1 do    sintable[len + i] := 0;end; procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  logo_h  := 768; logo_w := 768;  laz_tex := glLoadJPGToTexture('laz.jpg');  sintable := nil;  stay(800);          // fill 0, 800 time sin table  0,0,0,0,0,0,0.......  sinus(200, 320, 4); // amplitude , step, cycle number  stay(400);  sinus(20, 320, 8);  stay(200);  sinus(20, 60, 10);end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  y,c, offset, dstX, dstY,cx,cy: Integer;begin  cx := (OpenGLControl1.Width - logo_h) div 2;  cy := (OpenGLControl1.Height - logo_w) div 2;   glFillScreen(OpenGLControl1, 0.0, 0.2, 0.4, 1.0);   for y := 0 to logo_w - 1 do    begin      c := (table_index + y) mod Length(sintable); // c = sintable counter index      offset := sintable[c];      dstX := cx + offset;      dstY := cy + y;      glBlitCopy(laz_tex, 0, y, logo_h, y + 1, dstX, dstY,1.0, bmCopy);    end;   OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  table_index := (table_index + 2) mod Length(sintable);  // +2 sin offset !  OpenGLControl1.Invalidate;end; procedure TForm1.FormDestroy(Sender: TObject);begin  glClearAllTextures;end; end. ---------------------------------------------------------------------- Gigatron · 2025-08-23 22:36 Hi An example of roto zoom fx with glTiledTexture2D of glcanvas V0.043 or texture repeat use dynamic array of sintable. Rotozoom live example: https://www.youtube.com/watch?v=V9FSx_n_spk Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure glTiledTexture2D(x, y, w, h: GLfloat; texID: GLuint;                        patternWidth, patternHeight: GLfloat;                          scaleX: GLfloat = 1.0; scaleY: GLfloat = 1.0;                        rotation: GLfloat = 0.0;                          red: GLfloat = 1.0; green: GLfloat = 1.0;                          blue: GLfloat = 1.0; alpha: GLfloat = 1.0;                          FlipX: Boolean = False; FlipY: Boolean = False); If you want fullscreen Rotozoom replace TForm1.OpenGLControl1Paint by this code. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  cx, cy: Integer;begin  cx := (OpenGLControl1.Width - 4096) div 2;   cy := (OpenGLControl1.Height - 4096) div 2;  glFillScreen(OpenGLControl1, 0.0, 0.6, 0.8, 1.0);   glTiledTexture2D(cx, cy, 4096, 4096, hawk_tex,       // big screen size 4096x4096                 Round(256 + sin(sintmr) * 100), // de (256-100) à 256                 Round(256 + sin(sintmr) * 100),                 1.0, 1.0, sintable[tmr], 1.0,1.0,1.0, 1.0, false, false);   OpenGLControl1.SwapBuffers;end;   Regards ---------------------------------------------------------------------- Gigatron · 2025-08-26 22:29 Hi Photoshop blend shader port from ST author ben : https://www.shadertoy.com/view/XdS3RW 25 blend mode + 25 add Added some mixed functions you can add your blend function in memo1.text in fragment shader. You can play blend formula in shadertoy link for your own. eg: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i  vec3 myblend( vec3 s, vec3 d ){        return min(s,d)+1.-length(d);} vec3 icarus( vec3 s, vec3 d ){        return d*vec3(2.0*s.x + 0.5*s.x+0.2*s.z,                  1.2*d.x + 0.7*d.x+0.0*d.z,                0.5*s.x + 0.2*s.x+0.4*s.z);} vec3 laracolor( vec3 s, vec3 d ){        return cos(s*3.14)+sin(d*9.0);} vec3 icecolor(vec3 s,vec3 d) {                   vec2 resolution = vec2(1280.0, 720.0);             vec2 fragCoord = v_texcoord * resolution;             float wave = 0.5 + 0.5 * sin(10.0 * (length(texture2D(u_texture1, fragCoord/resolution).rgb) + 2.0));             return vec3(wave);}   The glcanvas v0.044 can now load two textures to make this blend shader. project1.zip contain demo with trackbar to display all 50 blend mode and you can save screenshot or region of screen in .jpg or .png format, see the example code. Textures are attached size 512x512 power of 2 in .jpg format . Have fun; ---------------------------------------------------------------------- Gigatron · 2025-08-30 01:28 Hi Late today, added some new commands in glcanvas v0.045; fix glDrawTexturePerspective added glArc, glRoundedRect,  glDrawShader normal shader + fix animation u_time. glDrawShader(x, y, w, h: GLfloat; shaderProgram: GLuint;                        red: GLfloat = 1.0; green: GLfloat = 1.0;                        blue: GLfloat = 1.0; alpha: GLfloat = 1.0;                        tm: GLfloat = 0.0); The last parameter tm is the speed of animation. Normal shader without texture example with less code and demo of gamecube boot anim from ST. https://www.shadertoy.com/view/tXdGDH Regards Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1;{$mode objfpc}{$H+}interfaceuses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls, StdCtrls,  OpenGLContext, glcanvas, gl;type  { TForm1 }  TForm1 = class(TForm)    Memo1: TMemo;    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end;var  Form1: TForm1;  shader_program : GLuint; implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  shader_program := glMakeShaderProgram('', Pchar(Memo1.Text));  if shader_program = 0 then raise Exception.Create('Shader Compilation Failed. ');end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);begin  glFillScreen(OpenGLControl1, 0.0, 0.0, 0.0, 1.0);  glDrawShader(0,0,1920,1280 ,shader_program,1.0,1.0,1.0,1.0,1.0);// u_time = speed of animation  OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  OpenGLControl1.Invalidate;end; end. ---------------------------------------------------------------------- Gigatron · 2025-09-01 22:25 Hi Here is another example with textured Shader and glCanvas 0.046 added function  glGetColor(x, y: Integer): TglColor; Get pixel color at x,y with r,g,b,a format. ** I'm going to join the 3T Games group to code some parts of a game with Unity, such as parallax scrolling, and additional codes with the c# language that I master well. So I would be less present on the lazarus forum. I would look here to see if anyone has any questions or issues with these two libraries. Fast Canvas & glCanvas ** Image from Cougar/Sanity Amiga; Regards Main unit; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls, StdCtrls,  ComCtrls, Spin, OpenGLContext, glcanvas, gl; type   { TForm1 }  TForm1 = class(TForm)    Button1: TButton;    Button2: TButton;    FloatSpinEdit1: TFloatSpinEdit;    Memo1: TMemo;    OpenGLControl1: TOpenGLControl;  Timer1: TTimer;    procedure Button1Click(Sender: TObject);    procedure Button2Click(Sender: TObject);    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end; var  Form1: TForm1;  hawk_tex : GLuint;  hawk_w, hawk_h: integer; // get texture size variables !!  shader_program : GLuint; implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  hawk_tex  := glLoadJPGToTexture('cougar.jpg',hawk_w, hawk_h);// source tex   shader_program := glMakeShaderProgram('', Pchar(Memo1.Text));  if shader_program = 0 then raise Exception.Create('Shader Compilation Failed. ');end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);begin  glFillScreen(OpenGLControl1, 0.0, 0.6, 0.8, 1.0);   glDrawTexturedShader(500,0,1024,960, hawk_tex, 0, shader_program, // 1 texture used !                       1.0,1.0,1.0,1.0,0);// static timer , tm=0 , no animation !   OpenGLControl1.SwapBuffers;end;// save region of openglcontrol1  with texture position + jpg quality  70%procedure TForm1.Button1Click(Sender: TObject);var  FileName: string;begin  FileName := 'mypic_.jpg';  try    glSaveRegionToJPG( FileName, 500, 0, 1024,960,70); // position of texture x,y,x1,y1    ShowMessage('Picture Saved : ' + FileName);  except    on E: Exception do      ShowMessage('Error : ' + E.Message);  end;end; procedure TForm1.Button2Click(Sender: TObject);var  FileName: string;begin  FileName := 'mypic_.jpg';  try    glSaveScreenShotJPG( FileName,90);  ShowMessage('Picture Saved : ' + FileName);  except    on E: Exception do      ShowMessage('Error : ' + E.Message);  end;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  glSetUniformFloat(shader_program, 'intensity',FloatSpinEdit1.value);  OpenGLControl1.Invalidate;end; procedure TForm1.FormDestroy(Sender: TObject);begin  glClearAllTextures; // free all loaded texturesend; end. ---------------------------------------------------------------------- Gigatron · 2025-09-11 22:57 Hi A new version of glCanvas v0.047 with alpha corrections on some commands, added glPolygon (glpoint : TglPoint array). x,y pos, Tglpoint, r,g,b,a,Filled,Thickness,angle,scalex,y. glBlitCopy with more gl blendmode and rotation. Demo example is included in project1.zip. Have Fun PS: I am busy with some project so if you want new commands or suggestions please PM me. ---------------------------------------------------------------------- Gigatron · 2025-09-13 21:58 Hi Let me introduce a new version of glCanvas v0.048 with some nice effect; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i glMoveToTexture2D(-800, 700, 1600, 700, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etLinear); Move texture from : x,y to x1,y1, in 3.0 sec, tex_width, tex_height,texture , scaleX,Y, teint r,g,b,a, flipX,Y,AnimLoop,easing type Assing Movement to texture ; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i glMovementTexture2D(800, 300,   0,300, 10.0, mtLinear,   tex_w, tex_h, texture, tex,0.5,0.5,rot, 1.0,1.0,0.0,1.0); x,y, radiusX,Y, 10.0 sec, movement type, tex_w,h, scalex,y,rotation,teint r,g,b,a,flipx,y,animloop Demo is included in project1.zip Have Fun ; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1; {$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls,  OpenGLContext, glcanvas, gl; type  { TForm1 }  TForm1 = class(TForm)    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end; var  Form1: TForm1;  tex: GLuint;  tex_w, tex_h: integer;  rot: single; implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);      // initialisation OpenGL  glEnableVSync(true);         // synchro verticale activée  tex := glLoadPNGToTexture('girl7.png', tex_w, tex_h); // exemple de texture  rot := 0.0;end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);begin  glFillScreen(OpenGLControl1, 0.2, 0.2, 0.2, 1.0);   glMoveToTexture2D(-800, 700, 1600, 700, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etLinear);  glMoveToTexture2D(-800, 600, 1600, 600, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etEaseIn);  glMoveToTexture2D(-800, 500, 1600, 500, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etEaseOut);  glMoveToTexture2D(-800, 400, 1600, 400, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etEaseInOut);  glMoveToTexture2D(-800, 300, 1600, 300, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etBounceOut);  glMoveToTexture2D(-800, 200, 1600, 200, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etElasticOut);  glMoveToTexture2D(-800, 100, 1600, 100, 3.0, tex_w, tex_h, tex, 0.5, 0.5, 0, 1.0, 1.0, 1.0, 1.0,False, False, true, etBackOut); //etLinear, etEaseIn,etEaseOut,etEaseInOut,etBounceOut,etElasticOut,etBackOut   glMovementTexture2D(800, 300,   0,300, 10.0, mtLinear,   tex_w, tex_h, tex,0.5,0.5,rot, 1.0,1.0,0.0,1.0);  glMovementTexture2D(800, 200, 600,200, 10.0, mtSinus,    tex_w, tex_h, tex,0.5,0.5,-rot,0.0,1.0,0.0,1.0);  glMovementTexture2D(800, 200, 600,200, 10.0, mtCircular, tex_w, tex_h, tex,0.5,0.5);  glMovementTexture2D(800, 200, 600,200, 10.0, mtSpiral,   tex_w, tex_h, tex,0.5,0.5);  glMovementTexture2D(800, 200, 600,200, 10.0, mtFigure8,  tex_w, tex_h, tex,0.5,0.5);  glMovementTexture2D(800, 200, 600,200, 10.0, mtZigZag,   tex_w, tex_h, tex,0.5,0.5);  glMovementTexture2D(800, 200, 600,200, 10.0, mtOrbital,   tex_w, tex_h, tex,0.5,0.5); //mtLinear, mtSinus, mtCircular, mtSpiral, mtFigure8, mtZigZag,mtOrbital   glDrawText3D(600,200,'GL MOVETO AND MOVEMENT DEMO',4,4,1.0,1.0,1.0,1.0,0.8,0.8,0.8,'Impact',34,[],rot,true);   OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  rot += 1.2;                  // incrémente l'angle  OpenGLControl1.Invalidate;   // redessineend; procedure TForm1.FormDestroy(Sender: TObject);begin  glClearAllTextures;        // libère toutes les textures  glClearTextCache;end; end. ---------------------------------------------------------------------- Gigatron · 2025-09-16 21:51 Hi The next version status details of the glCanvas V0.049 with some new commands taken from FastCanvas V1.052. Will upload this version soon, you can see the live result on my YT Channel; One version to reach V0.050 the final release; Regards https://www.youtube.com/watch?v=HiXpe75j-i8 ---------------------------------------------------------------------- 440bx · 2025-09-16 23:16 It's looking really good. Looking forward to the final version.   Thank you for sharing. ---------------------------------------------------------------------- Gigatron · 2025-09-20 21:50 Quote from: 440bx on September 17, 2025, 01:16:47 amIt's looking really good. Looking forward to the final version.   Thank you for sharing. Thank you @440bx So you can do some nice fx with this glcanvas V0.049.. contain now some Vector Text draw, Centered drawText, 2D/3D SpriteStarfield ... Texture Bounce 255 max ! mtVector movement .. mt mean Movement Type defined like this: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i TGLMovementType = (    mtLinear,    mtSinus,    mtCircular,    mtSpiral,    mtFigure8,    mtZigZag,    mtVector,    mtTriangle,    mtBreakOut  );   All textures are included in the  .zip file. Do you have any ideas for effects to include for the final version? Have fun ; ---------------------------------------------------------------------- 440bx · 2025-09-20 23:36 @Gigatron, My pleasure. Quote from: Gigatron on September 20, 2025, 11:50:17 pmDo you have any ideas for effects to include for the final version? As far as ideas, one effect I really like is the "glow effect".   Sort of an example of it can be found at https://forum.lazarus.freepascal.org/index.php/topic,58138.msg433109.h tml#msg433109 Another place where it was used is/was in the Windows logo when booting Windows 7.  Those are the two examples that come to mind at this time. ---------------------------------------------------------------------- Gigatron · 2025-09-21 22:15 Hi Here two example on the left with pixelshader(blur)  and the right glcommand : glDrawTexture2DGlow; I think the windows7 boot screen is made with gaussian blurfx. Please test this project. Regards ---------------------------------------------------------------------- elkhalafy · 2025-09-23 17:43 Download the library please? ---------------------------------------------------------------------- Gigatron · 2025-09-23 19:15 Quote from: elkhalafy on September 23, 2025, 07:43:14 pmDownload the library please? Hi You must download project1.zip above (glCanvas.pas) is included; Regards ---------------------------------------------------------------------- elkhalafy · 2025-09-24 06:27 Quote from: Gigatron on September 23, 2025, 09:15:23 pmQuote from: elkhalafy on September 23, 2025, 07:43:14 pmDownload the library please? Hi You must download project1.zip above (glCanvas.pas) is included; Regards Okay, Thank you ---------------------------------------------------------------------- Gigatron · 2025-10-05 21:37 Hi This is the Final release of glCanvas 0.50 some nice fx were added like Faster than light outline text draw , auto centeredX text .. etc.. Atom demo included with amigadigital88 font.. Have fun ---------------------------------------------------------------------- DrakkTheSeafarer · 2025-10-06 08:53 Thank you for sharing. ---------------------------------------------------------------------- cris75 · 2025-10-08 14:46 Hi, Thank you for sharing. I'm on Debian 12 (KDE / X11) had this error trying to compile project1 QuoteglCanvas.pas(1246,25) Error: Identifier not found "glXGetProcAddress" In case it could be useful to someone else, to "fix" it I just needed to comment out line 1242 Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i //glXSwapIntervalSGI := nil; and change line 1246 to Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i Pointer(glXSwapIntervalSGI) := wglGetProcAddress(PAnsiChar('glXSwapIntervalSGI')); ---------------------------------------------------------------------- Gigatron · 2025-10-08 16:41 Quote from: cris75 on October 08, 2025, 04:46:28 pmHi, Thank you for sharing. I'm on Debian 12 (KDE / X11) had this error trying to compile project1 QuoteglCanvas.pas(1246,25) Error: Identifier not found "glXGetProcAddress" In case it could be useful to someone else, to "fix" it I just needed to comment out line 1242 Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i //glXSwapIntervalSGI := nil; and change line 1246 to Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i Pointer(glXSwapIntervalSGI) := wglGetProcAddress(PAnsiChar('glXSwapIntervalSGI')); Hi , Thanks for testing with linux. You mean like that ? If so i will update the glCanvas. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i  // pour linux .. a voir si ça marche !! correction le 08/10/2025 18h38  {$IFDEF LINUX} //  glXSwapIntervalSGI := nil;  {$ENDIF}   {$IFDEF LINUX}  Pointer(glXSwapIntervalSGI) := glXGetProcAddress(PAnsiChar('glXSwapIntervalSGI'));  if not Assigned(glXSwapIntervalSGI) then    raise Exception.Create('GLX_SGI_swap_control not supported by driver');   if Enable then    glXSwapIntervalSGI(1)  else    glXSwapIntervalSGI(0);  {$ENDIF} ---------------------------------------------------------------------- cris75 · 2025-10-08 17:10 Hi, yes but note line 1246 (line 7 in the code snippet), not glXGetProcAddress but wglGetProcAddress, this way it complies for me glXGetProcAddress is not found Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   // pour linux .. a voir si ça marche !!  {$IFDEF LINUX}   //glXSwapIntervalSGI := nil;  {$ENDIF}   {$IFDEF LINUX}  Pointer(glXSwapIntervalSGI) := wglGetProcAddress(PAnsiChar('glXSwapIntervalSGI'));  if not Assigned(glXSwapIntervalSGI) then    raise Exception.Create('GLX_SGI_swap_control not supported by driver');   if Enable then    glXSwapIntervalSGI(1)  else    glXSwapIntervalSGI(0);  {$ENDIF} ---------------------------------------------------------------------- Gigatron · 2025-10-08 17:29 Ok This version fix linux compilation error and include some new commands like plasma, flag ,FBM plasma(internal shader) , UV scrolling and some memory leaks fix. No need to free texture, chars  and shaders ondestroy Form1. Regards ---------------------------------------------------------------------- cris75 · 2025-10-09 08:16 Works great, thank you!! ---------------------------------------------------------------------- indydev · 2025-11-25 06:16 I removed the windows dependencies of NativeFastCanvas, so I could test it on Linux. Just replace the unit in any of the test projects that have been uploaded and they should work on Linux and Mac (though I didn't test it on MacOS). Should work on Windows too. ---------------------------------------------------------------------- Gigatron · 2025-11-26 13:11 Quote from: indydev on November 25, 2025, 07:16:25 amI removed the windows dependencies of NativeFastCanvas, so I could test it on Linux. Just replace the unit in any of the test projects that have been uploaded and they should work on Linux and Mac (though I didn't test it on MacOS). Should work on Windows too. I made a long trip over several weeks, I will see to continue some projects on lazarus pascal. That said, you have done an excellent job, thank you very much, I hope that all W.,L.M users will enjoy it. Regards GTR ---------------------------------------------------------------------- indydev · 2025-11-27 09:35 Quote from: Gigatron on November 26, 2025, 02:11:15 pm ...you have done an excellent job, thank you very much, I hope that all W.,L.M users will enjoy it. Regards GTR Thanks for the kind words. I wondered if using the GTKWidgets directly would improve the speed on Linux, but I couldn't get that to work. Not sure how this version compares on Windows to your original, but I always try to find the most fpc friendly methodology if possible. ---------------------------------------------------------------------- elkhalafy · 2025-12-19 06:40 Create GitHub page for your projects with latest updates, Downloads, better. Thank you ---------------------------------------------------------------------- Gigatron · 2025-12-31 22:58 Quote from: elkhalafy on December 19, 2025, 07:40:13 amCreate GitHub page for your projects with latest updates, Downloads, better. Thank you Hi , Sorry for the late answer but sure no time with github, consider the latest version is included in latest demo... Like here; This is the bugfixed and added some internal shader version of glCanvas of 2025. Some Shaders are copyrighted so use them for non commercial usage. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i PlasmaFBMShader: GLuint = 0;  free PlasmaShader: GLuint    = 0;   free PlanetShader: GLuint    = 0;  not free FlagShader: GLuint      = 0;   free GlowShader: GLuint      = 0;  free PhongBallShader: GLuint = 0; free PulstarShader: GLuint   = 0;   free StarNestShader: GLuint  = 0;  not free CounterShader: GLuint   = 0; modifyed partial free  New year demo live exemple; https://www.youtube.com/watch?v=oJjeNA3-JhY ---------------------------------------------------------------------- Gigatron · 2026-01-08 17:57 Hi Added Bitmap font demo + Amiga (fake  ) Decruncher please see demo simple code. Regards ---------------------------------------------------------------------- Gigatron · 2026-01-10 23:19 Hi , Time really flies when you’re coding 🙂 I’m sharing a debugged version of glCanvas with a nice demo included. Code under 100 lines; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1;{$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls,  OpenGLContext, glcanvas, gl, Math; type  { TForm1 }  TForm1 = class(TForm)    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end; var  Form1: TForm1;  tmr, rr,gg,bb : Single;  counter : integer;  tex , fond : GLuint;  tex_w, tex_h, fond_w, fond_h : integer; implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  glEnableVSync(True);  Randomize;  tmr := 0.0; // float  rr := random(); gg := random(); bb := random();  counter := 0;  tex  :=  glLoadPNGToTexture('gfx/laz.png',tex_w,tex_h);  fond :=  glLoadPNGToTexture('gfx/lazh.png',fond_w,fond_h);end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  i,j : integer;begin  glFillScreen(OpenGLControl1, 0.3, 0.3, 0.3, 1.0);     for i:=0 to 6 do      for j:=0 to 4 do    begin    glDrawTexture2DScroll(j*416,i*150 ,fond_w,fond_h,fond,(tmr/30.0)*float(1.+i),0.0, // cast i ; H-scrolling                          1.0,1.0,1.0,1.0,0.0,                        rr,gg,bb,1.0,false,false); // color + H & V Flip = false  end;   glTubeShader(500,200,tex_w,tex_h,tex,tmr,30,1.2,0.02); // new tubeShader; negate -tmr to inverse movement !   OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  tmr := tmr + 0.1;  counter := (counter + 1) mod 100; // reset counter   if (counter>=99) then  // reset rgb  begin    rr := random(); gg := random(); bb := random();  end;   OpenGLControl1.Invalidate;end; end. Regards GTR ---------------------------------------------------------------------- Roland57 · 2026-01-11 04:40 @Gigatron Tested successfully your latest (beautiful) demos under Linux. I don't why, when I open any of the projects, I get this warning: Unable to find the component class "TOpenGLControl". But, after that, I can compile and run the demo.  By the way, I don't get that warning when I open /examples/openglcontrol/openglcontrol_demo.lpi. ---------------------------------------------------------------------- Gigatron · 2026-01-11 12:35 Quote from: Roland57 on January 11, 2026, 05:40:12 am@Gigatron Tested successfully your latest (beautiful) demos under Linux. I don't why, when I open any of the projects, I get this warning: Unable to find the component class "TOpenGLControl". But, after that, I can compile and run the demo.  By the way, I don't get that warning when I open /examples/openglcontrol/openglcontrol_demo.lpi. Hi, i can not reproduce this warning issue and i'am not on Linux , maybe it's Path problem on Linux... Can you open project1.lpi and change this line 4:     To Save and Reload the project1 to Run. Don't know if this will fix the warning message. ** /examples/openglcontrol/openglcontrol_demo.lpi  ** In this .lpi the PathDelim is not present , so maybe we can delete the line One day i will Go to Linux Regards ---------------------------------------------------------------------- Gigatron · 2026-01-13 16:15 Hi There is a nice fx on Amiga Called Candy Bar .. You can see that fx here : https://www.youtube.com/watch?v=TZ_GZC6If3c Or here at Thyrone  : https://www.youtube.com/watch?v=Z7HV5hqCGVQ Or shaderform at shadertoy ; https://www.shadertoy.com/view/MtyGDR Or pascal code in glCanvas with internal shader with no music Live demo on my YT Channel; https://www.youtube.com/watch?v=sZoFVrm88t4 Sure Quantum Packer V5.0 is not exist and it's impossible to put shadow of the beast into 1 amiga disk 880 kb + 79 track + 4 track So the cracktro is fake Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1;{$mode objfpc}{$H+} interface uses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls,  OpenGLContext,  glcanvas, gl, Math; const     DEMO_TEXT = 'HI AND WELCOME GIGATRON PRESENTS SHADOW OF THE BEAST CRACKED ' +              'TRAINED AND COMPACTED TO ONE DISK WITH QUANTUM DATA PACKER V 5.0 ' +              '    ENJOY TECHNOLOGY AND SEE YOU ON ANOTHER PRODUCTION BYE BYE      '; type  { TForm1 }  TForm1 = class(TForm)    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end; var  Form1: TForm1;  tmr, rr,gg,bb : Single;  counter : integer;   // bitmap font !  fnt: GLuint;  fnt_tmr : Single;  fnt_w, fnt_h : integer;  // Amiga decruncher & the rest    adosb,adosf : GLuint;    decrunchFinished: Boolean;    decrunchDuration: Integer;     adosb_w,adosb_h,adosf_w,adosf_h: integer; implementation {$R *.lfm} procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  glEnableVSync(True);  Randomize;  tmr := 0.0; // float  fnt_tmr := 0.0;  rr := random(); gg := random(); bb := random();  counter := 0;   fnt   := glLoadPNGToTexture('fonts/32/025_32.png', fnt_w, fnt_h);   adosb := glLoadPNGToTexture('gfx/amdos.png', adosb_w, adosb_h);        // AmigaDos Back  adosf := glLoadPNGToTexture('gfx/amdos2.png', adosf_w, adosf_h);      // AmigaDos Front   // Initialiser le decrunch  decrunchFinished := False;  decrunchDuration := 0; // decrunch duration end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var    cw, ch: integer;begin  glFillScreen(OpenGLControl1, 0.1, 0.1, 0.1, 1.0);  cw := OpenGLControl1.Width ;  ch := OpenGLControl1.Height  ;   if not decrunchFinished then // not finished      begin        glDecrunchBars(cw,ch, 20, decrunchDuration);        Inc(decrunchDuration);        glDrawTexture2 D(600,300,adosb_w,adosb_h,adosb,2.5,2.5,0.0,1.0,1.0,1.0,1.0);        glDrawTexture2D(598,68, adosf_w,adosf_h,adosf,2.5,2.5,0.0,1.0,1.0,1.0,1.0);         if decrunchDuration >= 250 then decrunchFinished := True;       end  else        // decrunch end ? continue :)  begin   glStarFieldShader(0, 0, cw, ch, tmr, 1.0, 0.0, 8, 1.0, 1.0, 1.0, 1.0);   glDrawVectorText3DSolid(0, 40, 0,'GIGATRON',  30, 4,  // 3D Space pos x,y,z !!    2, cw, ch,180.0, -tmr*8.0, 0.0, 0.8, 1.0, 1.0, 1.0,    Cos(tmr * 0.4) * 40, Sin(tmr * 0.2) * 80, 0.8 );   glCandyBarShader(0, 0, 1980, 130, tmr/3.0, 0.0, 20.0, 1.0, 1.0, 1.0,                   rr, gg, bb,1.0);   glCandyBarShader(0, 884, 1980, 130, -tmr/3.0, 0.0, 20.0, 1.0, 1.0, 1.0,                   rr, gg, bb, 1.0);   glBitmapFontText(fnt, Round(8000 - fnt_tmr  ), 710-50*abs(sin(tmr*0.48)*5.0),                       DEMO_TEXT, 32, 32, 10, 1.0, 0.0, bmMax, 6.0,6.0);  end;   OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  tmr := tmr + 0.1;  fnt_tmr := (fnt_tmr + 15.0) mod 52000;   counter := (counter + 1) mod 100;  if (counter >= 99) then  // reset colors  begin    rr := random();    gg := random();    bb := random();  end;  OpenGLControl1.Invalidate;end; end. ---------------------------------------------------------------------- Gigatron · 2026-01-16 23:44 Hi In the past i 've made a nice fx shader for construct2 : http://gigatron3k.free.fr/html5/C2/FX/ffill/ to replicate that quick coded demo made with gl Canvas (latest version). some new flood fx added with playin formula with the new command glFloodShader. Live example on YT : https://www.youtube.com/watch?v=Ptav4ISPOwo ** Ok the project is ready, just replaced Girl by Full Contact Amiga Picture Have Fun Regards ---------------------------------------------------------------------- Gigatron · 2026-01-17 13:34 Hi The next goal is Sampling OpenglControl1... with this post processing technic , we can add shader for all Screen this will affect all demo . Stay Tuned ! glScreenShaderCRT ... glScreenShaderRGBA ... etc I made this for MMF fusion 2  Html version to copy normal canvas to glCanvas ! Online YT demo working on 85% .. : https://www.youtube.com/watch?v=cH6Tiv5Y5j8 Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-02-08 01:25 Nice , This time the goal was to sampling all glCanvas to apply shader , result is ok now ! An example demo is included with CRT and glscreenwave Shader + Delta music reduced .dll + module by Dr. Gang + the latest version of GlCanvas with many new FX !! If you want Font color never black change openglcontrol1.paint like this ; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  i, yPos,cx,cy: Integer;begin  glFillScreen(OpenGLControl1, 0.1, 0.1, 0.1, 1.0);   cx := OpenGLControl1.Width div 2;  cy := OpenGLControl1.Height div 2;  // glTextureWave(cx -(tex_w div 2),cy-(tex_h div 2),tex_w,tex_h,tex,tmr*0.05,1.0,1.0,2.0,1.0);  // font color never become Black !!  glFontCopperShader(tmr*0.0, 32.0, 0.95, 1.0,                 0.0, 0.0, 0.0,                   0.5 + abs(sin(tmr*0.1)) * 0.5,                   0.5 + abs(sin(tmr*0.2)) * 0.5,                 0.5 + abs(cos(tmr*0.3)) * 0.5,                   0.0, 0.0, 0.0                 );   // Scrolling text  yPos := 1200;  for i := 0 to High(tx) do  begin     glBitmapFontText(fnt8, 80, yPos - txtPosY, tx[i], 8, 8, 60, 1.0, 0.0, bmLighten, 6.0, 6.0);    yPos := yPos + 70;  end;   glFontCopperShader(tmr*0.04,16.0,0.90,1.0,                   0.0,0.0,1.0,                     1.0,1.0,1.0,                     0.0,0.0,1.0                     );   glBitmapFontText(fnt,50,50,'',30,48,12,1.0,0.0,bmAdd,4.0,4.0);   glScreenShaderWave(OpenGLControl1, tmr * 0.4, 0.04, 8.0, 0.0, 1.0,false);   glScreenShaderCRT(OpenGLControl1, 0.95, 1.0, 2.0, 1.0, 1.0, 1.0, 1.0, 2.0);   OpenGLControl1.SwapBuffers;end;                     Or you can define the wave limit From bottom 0.0 to top 1.0 ; and add starfield shader to top. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  i, yPos,cx,cy: Integer;begin  glFillScreen(OpenGLControl1, 0.0, 0.0, 0.0, 1.0);   cx := OpenGLControl1.Width div 2;  cy := OpenGLControl1.Height div 2;   glStarFieldShader(0,0,1980,210,tmr*4.0,-1.0,0.0,10,1.0,1.0,1.0,1.0);   glFontCopperShader(tmr*0.0, 32.0, 0.95, 1.0,                   0.0, 0.0, 0.0,                   0.5 + abs(sin(tmr*0.1)) * 0.5,                 0.5 + abs(sin(tmr*0.2)) * 0.5,                   0.5 + abs(cos(tmr*0.3)) * 0.5,                   0.0, 0.0, 0.0                 );   // Scrolling text  yPos := 1200;  for i := 0 to High(tx) do  begin     glBitmapFontText(fnt8, 80, yPos - txtPosY, tx[i], 8, 8, 60, 1.0, 0.0, bmAdd, 6.0, 6.0);    yPos := yPos + 70;  end;   glFontCopperShader(tmr*0.04,16.0,0.90,1.0,                     0.0,0.0,1.0,                     1.0,1.0,1.0,                     0.0,0.0,1.0                     );   glBitmapFontText(fnt,50,10,'',30,48,12,1.0,0.0,bmAdd,4.0,4.0);   glScreenShaderWave(OpenGLControl1, tmr * 0.4, 0.04, 8.0, 0.0, 0.72,false); // define limit of wave                                                                           // Bottom to Top !  glScreenShaderCRT(OpenGLControl1, 0.95, 1.0, 2.0, 1.0, 1.0, 1.0, 1.0, 2.0);   OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  tmr := tmr + 0.1;  txtPosY := txtPosY + 2;  if txtPosY > 900 then txtPosY := 900;   OpenGLControl1.Invalidate;end; Have Fun Gigatron ---------------------------------------------------------------------- Gigatron · 2026-02-08 14:57 Hi I finished a nice intro with the latest Glcanvas, CRT + Text Effect(coded) and delta music in action ; in live video : https://www.youtube.com/watch?v=0z6D4tK55us Regards ---------------------------------------------------------------------- backprop · 2026-02-08 19:22 Interesting retro demos you have here, but this is just windows related? ---------------------------------------------------------------------- Gigatron · 2026-02-08 19:59 Quote from: backprop on February 08, 2026, 08:22:41 pmInteresting retro demos you have here, but this is just windows related? Don't know  about Linux & Mac OS; but all functions (more than 100) of Glcanvas uses opengl 2.0, there many project uploaded in this topic, you must test them. I'm Sure some functions are working on both system except music player wich use windows audio . Regards ---------------------------------------------------------------------- backprop · 2026-02-08 20:24 Yes, after removing code for music and fixing case sensitive directory name with Linux, last project works... Too bad music is just Windows related. I will try previous ones, some demos looks quite nice on your YouTube channel... One suggestion, though. Instead creating project1.zip, it would be great to create some meaningful name of the zip in order to distinguish all when download. ---------------------------------------------------------------------- Gigatron · 2026-02-10 15:40 Hi The latest version of Glcanvas with more Amiga like Fx; Live demo on YT : https://www.youtube.com/watch?v=pGgl3gBavQ4 Regards ---------------------------------------------------------------------- backprop · 2026-02-10 22:38 For some older demos which can't compile with older glCanvas, missing glLoadPNGToTexture with right number of parameters when replaced with new glCanvas. Example, demo which uses this code, for instance: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   TexFond   := glLoadPNGToTexture('sotb/fond.png');  TexMontagne := glLoadPNGToTexture('sotb/montagnes.png');  TexNuage0   := glLoadPNGToTexture('sotb/nuages0.png');  TexNuage1   := glLoadPNGToTexture('sotb/nuages1.png');  TexNuage2   := glLoadPNGToTexture('sotb/nuages2.png');   Can't be specific which, as older zip files had the same name and I have downloaded many  at once... EDIT: After adding required variables as dummy code, at least can compile and show something... ---------------------------------------------------------------------- Gigatron · 2026-02-11 13:54 Hi, As I explained earlier in this topic, glCanvas evolves between versions and each version comes with its own demo examples. The new version is not compatible with old demos. The demos are designed to work with their specific glCanvas version. Latest glCanvas is now v0.051 ++ added more and more commands; API changes between versions (like glLoadPNGToTexture now requiring width/height parameters to retrive Texture width and height ) Be sure when it's done i will try to adapt required old demo ... (google translate) In addition the next version demo example glTextureTunnelShader.  https://www.youtube.com/watch?v=RvLYKVtL-Gw Regards Gigatron ---------------------------------------------------------------------- backprop · 2026-02-11 19:15 Some old demos are quite nice, but use version which is not supported by Linux. It would be nice if you make it available on you site or here upgraded... ---------------------------------------------------------------------- Gigatron · 2026-02-12 22:24 Quote from: backprop on February 11, 2026, 08:15:33 pmSome old demos are quite nice, but use version which is not supported by Linux. It would be nice if you make it available on you site or here upgraded... Hi, is this demo is working for you ? Regards ---------------------------------------------------------------------- backprop · 2026-02-13 10:36 Quote from: Gigatron on February 12, 2026, 11:24:44 pmHi, is this demo is working for you ? Regards After removing part for playing audio, fixed some case sensitive filenames and adding missing texture, it can compile and it works on Linux. Thanks. I will do something with audio support for Linux, though. Great retro demo without great retro music is half complete... ---------------------------------------------------------------------- Gigatron · 2026-02-13 18:07 Good Missing 1 or 2 shader and i will release glCanvas V1.0 ... glScreenPixelate & ??? a crazy shader Latest live demo ; glRaserBarShader, glFloorShader, glScreenQuantizeShader and so on  ...  https://www.youtube.com/watch?v=oBK2G3-jyKs ---------------------------------------------------------------------- backprop · 2026-02-13 18:16 Better demo with fast color changing... But music is a bit slow. Great demo! ---------------------------------------------------------------------- Gigatron · 2026-02-14 00:14 Quote from: backprop on February 13, 2026, 07:16:49 pmBetter demo with fast color changing... But music is a bit slow. Great demo! For the release 1.0 of glCanvas i have added some nice shader from my old Construct Fx shader; Screen Palettes from C64, CPC , ZX  ... screen Resolution ... Screen3D, ScreenCube .... and so .. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.OpenGLControl1Paint(Sender: TObject);var   cx, cy,i: Integer;   col1, col2,col3 : TglColor;begin  glFillScreen(OpenGLControl1, 0.1, 0.1, 0.1, 1.0)  ;  cx := OpenGLControl1.Width div 2;  cy := OpenGLControl1.Height div 2;    glStarFieldShader(0,0,1980,700,tmr*2.0,1.0,0.0,8,1.0,1.0,1.0,1.0);    glBitmapFontText(fnt32,106,36,'GIGATRON 2026',32, 32, 10, 1.0, 0.0, bmAlpha, 4.0, 4.0);   glRasterShader(tmr*0.2, 1980, 300, 180, 4, 256.0, 1.0, 1.0, 0.0, 1.0, 0.0, 0.0);  glRasterShader(-tmr*0.2, 1980, 300, 10, 4, 256.0, 1.0, 1.0, 0.0, 1.0, 0.0, 0.0);   glTextureFloorShad er(0,300,1980,750,tex,-tmr*0.1,0.45,0.4,6.0,0.5,0.5,0.5);   col1.r:= 0.0;     // black  col1.g:= 0.0;  col1.b:= 0.0;  col1.a:= 1.0;   col2.r := 0.5 + abs(sin(tmr*0.3)) * 0.5;  col2.g := 0.5 + abs(sin(tmr*0.2)) * 0.5;  col2.b := 0.5 + abs(cos(tmr*0.1)) * 0.5;  col2.a := 1.0;   col3.r:= 0.0;   // black  col3.g:= 0.0;  col3.b:= 0.0;  col3.a:= 1.0;   for i := 0 to 7 do  // 8 copper bars  begin     glCopperBar(0,300+i*8+80*sin(ct/20+(i/2)),1980, 300+i*8+80*sin(ct/20+(i/2))+64 , col1,col2,col3,0.0,false,1.0);  end;     glBitmapFontText(fntx,                 2200 - txtPosx,               620,                 ' ... WELCOME GIGATRON PRESENTS - FLOOR AND SCREEN COLOR REDUCTION FX - GLCANVAS REACH SOON V1.0 OVER 100 ++ AMIGA STYLE FX GL COMMAND FOR LAZARUS PASCAL MAKE OLD CRACKTROS BECOME EASY ! SEE YOU BYE !!! ',                 32, 32, 10, 1.0, 0.0, bmAlpha, 3.0, 3.0);  // Before glBitmapFontFx command , Threshold is target color of bitmap font near white; // After this Shader All Bitmap Fonts are affected by this FX  glFontCopperShader(-tmr*0.05, 320, 256, 16.0, 0.95, 1.0,0,                   1.0, 0.0, 0.0,  // Bleu                   0.0, 0.0, 1.0,                   0.5 + abs(sin(tmr*0.3)) * 0.5,                   0.5 + abs(sin(tmr*0.2)) * 0.5,                   0.5 + abs(cos(tmr*0.1)) * 0.5,                 0.0, 1.0, 1.0);    glBitmapFontText(fnt32,                 100,30,'GIGATRON 2026',32, 32, 10, 1.0, 0.0, bmAlpha, 4.0, 4.0);  // glScreenResolutionShader(OpenGLControl1,256.0); // glScreenQuantizeShader(OpenGLControl1,sq);   //glScreen3DShader(OpenGL Control1,tmr*0.0,tmr*0.1,0.0,0.0,0.0,0.0,0.0,                                  // 2.0,1.5,0,0,1024.0);  // glScreenTVShader(OpenGLControl1, 1.0 - (tmr / 50.0));  TO do !!    glScreen3DCubeShader(OpenGLControl1, 0,0,tmr*0.2,tmr*0.1,tmr*0.3,-3.0,1.5);   glScreen8bitShader(OpenGLControl1, 256.0, PALETTE_C64);   glScreenShaderCRT(OpenGLControl1, 0.95, 1.0, 1.0, 1.0,1.0, 1.0, 1.0, 1.0);  OpenGLControl1.SwapBuffers;end; Regards ---------------------------------------------------------------------- backprop · 2026-02-14 00:32 I have moved code for audio and now it is much clearer main unit. I have also added definition MUSIC at the beginning of the main unit which should be enough to easily remove music until working on Linux support. When enable MUSIC definition, can you confirm it can compile and run on Windows with music? EDIT: I have removed some things in Object inspector, project.lpr and changed few things in sidmon_lib.pas and new file sid_player.pas, thus now all should be much more clearer and independent. BTW, I have also  removed DLL file from the ZIP, which should be present to compile and run on Windows and audio support. ---------------------------------------------------------------------- Gigatron · 2026-02-14 12:54 Hi Can compile when $DEFINE MUSIC is disabled , otherwise no. I will try to split code too; But before, i must finishing some works ; https://www.youtube.com/watch?v=9J3D96h_Wk8 PreRelease Demo; Screen x,y,z Rotations , pixelate , scanline, colormode .... Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure glScreen3DShader(glc: TOpenGLControl;                           rot_x: Single = 0.0;                           rot_y: Single = 0.0;                         rot_z: Single = 0.0;                           trx: Single = 0.0;                           try_: Single = 0.0;                         rlx: Single = 0.0;                           rly: Single = 0.0;                           zoom: Single = 2.0;                         intensity: Single = 1.0;                           colormode: Integer = 0;                           scanlinemode: Integer = 0;                           rezpixel: Single = 256.0); https://www.youtube.com/watch?v=lm0wZQccXf0 Regards ---------------------------------------------------------------------- backprop · 2026-02-14 16:46 Quote from: Gigatron on February 14, 2026, 01:54:59 pmI will try to split code too; But before, i must finishing some works ; https://www.youtube.com/watch?v=9J3D96h_Wk8 Oh, great! I can feel dizziness... ---------------------------------------------------------------------- Gigatron · 2026-02-16 20:07 Nice Again; Before releasing V1.0 of glCanvas (bug corrections on the way) I would like to share the pre release demo with lot of many nice fx; all demo under 500kb zip file with module and gfx ! Please play with parameters of some functions to make your own demo. Today RGBA screen shift fx and more. Have fun Gigatron For example if you want A500 ECS or A1200 AGA style copy & paste this code. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  col1, col2, col3 : TglColor;  page          : Integer;begin  glFillScreen(OpenGLControl1, 0.1, 0.1, 0.1, 1.0);  glStarFieldShader(0, 0, 1980, 700, tmr*2.0, 1.0, 0.0, 8, 1.0, 1.0, 1.0, 1.0);  glTextured3DCube(OpenGLControl1, 0.0, 5.0, 0.0, 100.0, laztex,                   tmr*2.0, tmr*3.0, 0.0, 1.0, 1.0, 1.0);   glRasterShader( tmr*0.2, 1980, 300, 180, 4, 256.0, 1.0, 1.0, 1.0, 0.0, 0.0, 1.0);  glRasterShader(-tmr*0.2, 1980, 300,  10, 4, 256.0, 1.0, 1.0, 1.0, 0.0, 0.0, 1.0);  glTextureFloorShader(0, 300, 1980, 750, tex, -tmr*0.02, 0.45, 0.4, 6.0, 0.5, 0.5, 0.5);  col1 := glMakeColor(0.0, 0.0, 0.0, 1.0);  col2 := glMakeColor(0.5 + abs(sin(tmr*0.3)) * 0.5,                      0.5 + abs(sin(tmr*0.2)) * 0.5,                      0.5 + abs(cos(tmr*0.1)) * 0.5, 1.0);  col3 := glMakeColor(0.0, 0.0, 0.0, 1.0);  glBitmapFontText(fntx,    2200 - txtPosX, 620,    ' *** WELCOME GIGATRON PRESENTS -  GLCANVAS PRE RELASE VERSION DEMO 2 - GLCANVAS REACH SOON V1.0 OVER 100 ++ AMIGA STYLE FX GL COMMAND FOR LAZARUS PASCAL MAKE OLD CRACKTROS BECOME EASY ! SEE YOU BYE *** ',    32, 32, 10, 1.0, 0.0, bmAlpha, 3.0, 3.0);  glFontCopperShader(-tmr*0.05, 320, 256, 16.0, 0.95, 1.0, 0,    0.0, 0.0, 1.0,    1.0, 1.0, 1.0,    0.5 + abs(sin(tmr*0.3)) * 0.5,    0.5 + abs(sin(tmr*0.2)) * 0.5,    0.5 + abs(cos(tmr*0.1)) * 0.5,    0.0, 0.0, 1.0);  glBitmapFontText(fnt32, 100, 30, 'GIGATRON 2026',    32, 32, 10, 1.0, 0.0, bmAlpha, 4.0, 4.0);   page := Trunc(tmr / 62.0) mod 8;   //glScreen3DShader(OpenGLControl1,tmr*0.02,0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -2.0, 2.0, 0, 0, 256.0);   case page of    0:      glScreenRGBA(OpenGLControl1,        1.0, 1.0, 1.0, 1.0,        sin(tmr*0.05) * 0.008, 0.0,        0.0, 0.0,        -sin(tmr*0.05) * 0.008, 0.0);    1:      glScreenRGBA(OpenGLControl1,        0.8, 0.9, 1.2, 1.0,        0.0, sin(tmr*0.06) * 0.006,        0.0, 0.0,        0.0, -sin(tmr*0.06) * 0.006);    2:      glScreenRGBA(OpenGLControl1,        1.2, 1.0, 0.7, 1.0,        0.0, 0.0, 0.0, 0.0, 0.0, 0.0);    3:      glScreenRGBA(OpenGLControl1,        1.0, 1.0, 1.0, 1.0,        sin(tmr*0.07) * 0.01,  sin(tmr*0.07) * 0.01,        0.0, 0.0,        -sin(tmr*0.07) * 0.01, -sin(tmr*0.07) * 0.01);    4:      glScreenRGBA(OpenGLControl1,        0.6, 1.2, 0.6, 1.0,        0.0, 0.0, 0.0, 0.0, 0.0, 0.0);    5:      glScreenRGBA(OpenGLControl1,      1.0, 1.0, 1.0, 1.0,        0.015, 0.0,        0.0,   0.0,        -0.015, 0.0);    6:      glScreenRGBA(OpenGLControl1,        0.8 + abs(sin(tmr*0.1)) * 0.4,        0.7, 0.7, 1.0,        0.0, 0.0, 0.0, 0.0, 0.0, 0.0);    7:      glScreenRGBA(OpenGLControl1,        0.9 + abs(sin(tmr*0.08)) * 0.3,        0.9 + abs(sin(tmr*0.06)) * 0.3,      0.9 + abs(cos(tmr*0.04)) * 0.3,        1.0,        sin(tmr*0.07) * 0.012,  sin(tmr*0.05) * 0.006,        0.0, 0.0,        -sin(tmr*0.07) * 0.012, -sin(tmr*0.05) * 0.006);  end;   // Amiga 1200 AGA Style  //  glScreenResolutionShader(OpenGLControl1,256.0);   // Amiga 500 ECS Style  glScreenResolutionShader(OpenGLControl1,128.0);   OpenGLControl1.SwapBuffers;end; ---------------------------------------------------------------------- backprop · 2026-02-17 02:19 This can't compile on Linux, unless I remove extra units in project1.lpr. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i program project1;...  Forms, lazopenglcontext, Unit1, glCanvas; //, soundtracker_lib, SoundtrackerAudio;  The thing is that compiler other way is forced to include these files, even they are not in use by declarations in main file and result is this: Code: [Select]Compile Project, Target: ./Glcanvas0051Demo/project1: Exit code 1, Errors: 1, Warnings: 1 Warning: linker: /usr/bin/ld: cannot find -lSoundtracker.dll: No such file or directory project1.lpr(23,1) Error: Error while linking And also notice that glCanvas is also not needed to be added here, nor lazopenglcontext, just this: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   Forms, Unit1; //lazopenglcontext, glCanvas, soundtracker_lib, SoundtrackerAudio;  Notice that every file you include in project inspector will be added here and if they are not essencial for functioning (as components, for instance), they will make problems. And one more thing... Linux as any UNIX system is case sensitive, meaning your file and path names need to be exact as they are wrote. In this case, you need to change "Font" name of directory to "font", or to replaces filenames in the code in order to use it. Otherwise, "Font" and "font" directories are not the same as in Windows. The same for files,  "echoing.mod" and "Echoing.mod" are not the same files. ---------------------------------------------------------------------- Gigatron · 2026-02-20 19:59 Hi This is the last debugged version and some nice fx of the Glcanvas. The old demos are not working with this version, (gl) was removed from uses in unit1 and Gluint was replaced by TGLTextureID; new type def ; So please  try this demo ; or live example on my YT channel; https://www.youtube.com/watch?v=HCwqh8yWklk Don't forget HeadPhone Regards ---------------------------------------------------------------------- Gigatron · 2026-02-24 16:48 Hi You know i'am working on glCanvas every day and make some intro to improve and debug the library. The latest one is  bitmap font multi sinus intro done by internal shader command. the live example a bit different : https://www.youtube.com/watch?v=bJ_UONnhTOw Be patient for V 1.0; Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-03-01 23:15 Nice Try to release V1.0 beta now ; Some new fx commands have 50000 parameters sorry Demo sound fonts are included with this nice library Glcanvas; Regards GTR ---------------------------------------------------------------------- Seenkao · 2026-03-02 02:32 Привет, Gigatron! Если интересно, то некоторую функциональность можно немного "упростить" и в понимании и в передаче данных. Например можно задавать цвет либо посредством структуры или посредством LongWord. В первом варианте мы создаём структуру и можно задать данные по умолчанию: Google translate: Hi, Gigatron! If you're interested, some functionality can be slightly simplified, both in terms of understanding and data transfer. For example, you can set the color either through a structure or through LongWord. In the first option, we create a structure and can set default data: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i type  myTColor = record    R, G, B, A: Single;  end;var                             // or constant  whiteColor: myTColor = (1, 1, 1, 1);  blackColor: myTColor = (0, 0, 0, 0); Во втором варианте мы из целого числа работаем только с байтами. В этом случае число LongWord - RRGGBBAA (или AARRGGBB). Различные варианты можно увидеть в разных движках и графических редакторах. Для передачи данных в процедуру или функцию, такие вещи проще. Просто передаём структуру или число RRGGBBAA и используем их. Возможно ещё проще создавать объекты и все данные хранить в объектах. А все функции и процедуры уже будут работать от самих объектов (в основном). Это только информация к размышлению! Успехов! Eng: In the second option, we work only with bytes from the integer. In this case, the LongWord number is RRGGBBAA (or AARRGGBB). Different options can be seen in different engines and graphic editors. Passing data to a procedure or function is simpler. We simply pass the RRGGBBAA structure or number and use it. It might be even easier to create objects and store all data in objects. And all functions and procedures will work from the objects themselves (mostly). This is just food for thought! Good luck! ---------------------------------------------------------------------- n7800 · 2026-03-02 03:36 Quote from: backprop on February 17, 2026, 03:19:31 amAnd also notice that glCanvas is also not needed to be added here, nor lazopenglcontext, just this: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   Forms, Unit1; //lazopenglcontext, glCanvas, soundtracker_lib, SoundtrackerAudio;  Notice that every file you include in project inspector will be added here and if they are not essencial for functioning (as components, for instance), they will make problems. By the way, this is controlled by the option with the long name: "Project Options > Miscellaneous > Main unit has Uses section containing all units of project". I'll add that some units, on the contrary, must be specified even if they are not explicitly used. For example, these are the standard cthreads and Interfaces units for a GUI application, since they have an initialization section that runs when the program starts. ---------------------------------------------------------------------- Gigatron · 2026-03-02 21:55 Quote from: Seenkao on March 02, 2026, 03:32:17 am Google translate: Hi, Gigatron! If you're interested, some functionality can be slightly simplified, both in terms of understanding and data transfer. For example, you can set the color either through a structure or through LongWord. In the first option, we create a structure and can set default data: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i type  myTColor = record    R, G, B, A: Single;  end;var                             // or constant  whiteColor: myTColor = (1, 1, 1, 1);  blackColor: myTColor = (0, 0, 0, 0); Hi thank you , i have the same color option on glCanvas; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i  TglColor = record    r, g, b, a: Single;  // r,g,b,a := glmakecolor(1.0,0.0,0.0,1.0); one time  end; And usage is like this : Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure TForm1.OpenGLControl1Paint(Sender: TObject);var   mycol : TglColor;begin   mycol := glMakeColor(1.0,0.0,0.0,1.0);   glFillScreen(OpenGLControl1, mycol.r,mycol.g,mycol.b,mycol.a); Regards ---------------------------------------------------------------------- Gigatron · 2026-03-02 21:57 Quote from: n7800 on March 02, 2026, 04:36:24 amQuote from: backprop on February 17, 2026, 03:19:31 amAnd also notice that glCanvas is also not needed to be added here, nor lazopenglcontext, just this: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i   Forms, Unit1; //lazopenglcontext, glCanvas, soundtracker_lib, SoundtrackerAudio;  Notice that every file you include in project inspector will be added here and if they are not essencial for functioning (as components, for instance), they will make problems. By the way, this is controlled by the option with the long name: "Project Options > Miscellaneous > Main unit has Uses section containing all units of project". I'll add that some units, on the contrary, must be specified even if they are not explicitly used. For example, these are the standard cthreads and Interfaces units for a GUI application, since they have an initialization section that runs when the program starts. Nice, and thank you, let's let users choose this ---------------------------------------------------------------------- Seenkao · 2026-03-02 22:20 Quote from: Gigatron on March 02, 2026, 10:55:07 pmAnd usage is like this : Заранее извиняюсь. Я возьму для примера твой кусочек кода. И применю "свои" правки. Google translate: My apologies in advance. I'll use your code snippet as an example and apply "my" edits. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure glDrawText(x, y: Integer; const txt: string;                     const textColor: TglColor = whiteColor;                                            // whiteColor - const or var                     fontName: string = 'Arial'; fontSize: Integer = 14;                     fontStyle: TFontStyles = [];                     Angle: Single = 0; CenteredRotation: Boolean = False;                     CenteredText: Boolean = False);begin  ...  glColor4fv(@textColor);   ...end.но лично я указателями пользуюсь. А вообще, большинство рекомендуют переходить на OpenGL 3+ или на Vulkan.  Eng: But personally, I use pointers. In general, most people recommend switching to OpenGL 3+ or Vulkan. ---------------------------------------------------------------------- Gigatron · 2026-03-02 23:18 Ok just made an overload procedure with pointer; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i // surcharge ; avec pointeurprocedure glDrawText(x, y: Integer; const txt: string;                     const textColor: TglColor  ;                   fontName: string = 'Arial'; fontSize: Integer = 14;                   fontStyle: TFontStyles = [];                     Angle: Single = 0; CenteredRotation: Boolean = False;                     CenteredText: Boolean = False); overload;   .............glColor4fv(@textColor);  usage;glDrawText(100,100,'HELL O',glMakeColor(1.0,1.0,1.0,1.0),'Arial',32); Thank you ---------------------------------------------------------------------- Gigatron · 2026-03-08 00:09 Hi Let me share the next beta version of Glcanvas; Live Version on YT; https://www.youtube.com/watch?v=QN4SPSge8vc Regards GTR ---------------------------------------------------------------------- Gigatron · 2026-03-09 19:32 Hi  My goal is almost achieved, out of the millions of possible effects on Amiga I managed to make a demo maker engine. Of course to have all the effects I need another 10 years:) By the way, I've almost finished the protracker player based on @Hukka's Propulse. A live demo of the player of a complex module and the latest beta version of Glcanvas with new effects. With GlCanvas you can do 1% of Existing Amiga Effects ; Texture twister based on Cravo - Twister . Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i // Twister, based on http://ddoodm.com/gen/Processing/Twister2.pde// main article here: http://ddoodm.com/wordpress/?p=104 void mainImage( out vec4 fragColor, in vec2 fragCoord ){           fragColor = vec4(0.0, 0.0, 0.0, 1.0);            float vamp = 1.0 + 2.0 * sin(iTime);    float roto = 2.0 + 2.0 * sin(iTime);        float fv = fragCoord.y / iResolution.y;    float deg90 = 0.5 * 3.14159;        float theta = iTime;    float x[4];        for (int i = 0; i < 4; i++ )    {        x[i] = 0.5 + 0.25 * sin(vamp * fv + roto + theta + deg90*float(i));  }        // Line colours        float lum[4];        for(int i=0; i<4; i++)        {               float len = 0.35+abs( x[i] - x[int(mod(float(i)+1.0,4.0))] );        lum[i] = 1.0 - len;        }          // Transform x[i] to clip coordinates        for(int i=0; i<4; i++)    {        x[i] = (x[i] * iResolution.x);        }        // Draw        for(int i=0; i<4; i++)        {        if(x[i] >= x[int(mod(float(i)+1.0,4.0))])  continue;         if ( fragCoord.x >= x[i] && fragCoord.x < x[int(mod(float(i)+1.0,4.0))] )        {             float v = mod(fragCoord.y, 128.0) / 128.0;                      float dx = x[int(mod(float(i)+1.0,4.0))] - x[i];            float u = (fragCoord.x - x[i]) / dx;                                   float c = lum[i];            c = c * c;            vec3 col = vec3(c,c,c) * texture(iChannel0,vec2(u,v)).xyz;            fragColor = vec4(sqrt(col),1.0);        }        }} // Glcanvas internal texture twister shader alot modifyed Cravo's source ; Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i void mainImage( out vec4 o, in vec2 p ){    const float TAU = 6.28318;  //2xPI    const float FACES = 4.0;     vec2 fc = p;    p = ((p/iResolution.y)-(iResolution.xy/iResolution.y)/2.);     float twist = iTime + 4.*sin(p.y)*2.0*cos(iTime);    float twidth = 0.3;    float fade = 1.0;     for(float i=0.; i= edge.x && p.x <= edge.y)        {          float dx = edge.y - edge.x;             float u = (p.x - edge.x) / dx;          // position dans la face            float v = fc.y / iResolution.y;       // répétition verticale             float shade = 0.4 + 0.6*abs(cos((i/FACES)*TAU + v));            vec3 tx = texture(iChannel0, vec2(u,v)).rgb;            o = vec4(tx * shade, 1.0)*fade;             return;        }    }     o = vec4(0.);} Projet not released .. protracker source code is really not finished and not cleaned yet . Live demo ; https://www.youtube.com/watch?v=cSxYDFl6vQc And the last beta demo on YT; https://www.youtube.com/watch?v=LCfW5PjYf4U Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-03-22 01:22 Hi Here is the Latest and Final Release of GlCanvas V1.0; This library include more and more fx with less code and used to make screen fx or Oldschool demo fx using lot of internal shader: PlasmaFBMShader, PlasmaShader, PlanetShader, FlagShader, WaveShader, GlowShader, PhongBallShader, PulstarShader, StarNestShader, CounterShader, TubeShader, StarFieldShader, CandyBarShader, FloodShader, FontCopperShader, FontReflectionShader, ScreenShaderWave, TunnelShader, FloorShader, RasterShader, CheckerBoardShader, CheckerLayerShader, TextureCopperShader, TwistShader, GridLine3DShader, TextureInterleaveShader, TextureParallaxShader, BamigaFloorShader, TextureBumpLightShader, DotTunnelShader, SquareTunnelShader, ShapeTunnelShader, SkyShader, SceneTransitionShader Screen Shader affect all glCanvas; ScreenShader, ScreenShaderCRT, QuantizeShader, ResolutionShader, Screen3DShader, Shader8bit, Screen3DCubeShader, ScreenTVShader, RGBAShader, ScreenMosaicShader, ScreenBinaryShader, ScreenCopperShader, ScreenReflectShader And other 2d , 3d primitives ; ** if you want special Fx or shaders let me know thx ** Have  Fun Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-04-14 18:39 Hi I am working for the next version of glCanvas V1.01 wich include some new visual effects .. Here is the last demo example of kaleidoscope shader made years ago with BGRA component. Add - glScreenGaussianBlur ; glScreenMotionBlur ; glScreenRotoZoom https://www.youtube.com/watch?v=3oHNFHjUboM Regards Gtr ---------------------------------------------------------------------- Gigatron · 2026-04-22 11:35 Hi Here is the latest and final version of glCanvas V1.1. There will be no further updates unless there are bug fixes or if you want a special effect. Missing vertex point editor , you can do this with coding. I think this library is more than enough to create demos of all kinds,  Amiga, C64, CPC, C64 and consoles style. So enjoy! Zip file include music( hukka protracker) and screen motion blur demo. Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-05-27 09:07 Hi Try to make game with glCanvas with latest version : added asciiartShader etc... Please test this shoot them up game; 1,2,3,4,5 key to change fire type.. all under 500 kb with no sound; The sprites from the old arcade game vulgus. Have fun Gtr ---------------------------------------------------------------------- microxa · 2026-05-29 18:43 Hi Gigatron!  Do you think about remastering the demo with the «Ocean Waves» shader? ---------------------------------------------------------------------- Gigatron · 2026-05-29 22:00 Quote from: microxa on May 29, 2026, 08:43:31 pmHi Gigatron!  Do you think about remastering the demo with the «Ocean Waves» shader? Hi, where is this 'Ocean Waves' shader ? This one ? http://gigatron3k.free.fr/html5/C2/FX/seasc/ Thx ---------------------------------------------------------------------- microxa · 2026-05-30 02:13 Quote from: Gigatron on May 30, 2026, 12:00:47 am Hi, where is this 'Ocean Waves' shader ? This one ? http://gigatron3k.free.fr/html5/C2/FX/seasc/ Thx Yes, it’s a demo (sorry for forgetting its exact name)...P.S.I don’t really understand such a complex topic.I had to dive deep into this wonder — it's truly amazing. Best regards, Gigatron! ---------------------------------------------------------------------- Gigatron · 2026-05-30 12:53 Hi @microxa Ok it's added to my todo list for next week after finishing the level2 of shoot them up. This shader called Seascape from TDM alias ; Alexander Alekseev. https://www.shadertoy.com/view/Ms2SD1 Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-06-02 00:09 Ok glcanvas v1.1 include now seascape shader by TDM; sfx by sunriders; Demo with protracker music with hukka protracker source all under 100   Lines of code. Have fun , Gtr Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i unit Unit1;{$mode objfpc}{$H+}interfaceuses  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ExtCtrls,  OpenGLContext, glCanvas, ProTracker.Util, ProTracker.Player, ProTracker_Audio; type  { TForm1 }  TForm1 = class(TForm)    OpenGLControl1: TOpenGLControl;    Timer1: TTimer;    procedure FormCreate(Sender: TObject);    procedure FormDestroy(Sender: TObject);    procedure OpenGLControl1Paint(Sender: TObject);    procedure Timer1Timer(Sender: TObject);  private  public  end;var  Form1: TForm1;  txtPosX, demotmr : Integer;  tmr, rot : single;  tex    : TGLTextureID;  tex_w,  tex_h       : Integer;   s_txt : String;   // font  fntx   : TGLTextureID;  fntx_w, fntx_h     : Integer; implementation{$R *.lfm}  procedure TForm1.FormCreate(Sender: TObject);begin  glInit(OpenGLControl1);  glEnableVSync(true);  s_txt := ' GIGATRON THE LEADER PRESENTS - GL SEASCAPE SHADER BY TDM - MADE WITH GL CANVAS V 1.1  LESS CODE MORE FUN ! SFX - SUNRIDERS  - GIGA GREETINGS TO ALL SCENERS AND LAZARUS FORUM MEMBERS SEE YOU BYE ... ';  fntx   := glLoadPNGToTexture('fonts/tri.png', fntx_w, fntx_h);  tex    := glLoadPNGToTexture('texture/city.png', tex_w,tex_h);   tmr := 0.0;  demotmr := 0;     // module  Module := TPTModule.Create(True, False);  Module.Stop;  Module.LoadFromFile('modules/e2.mod');  PT_Audio_SetPaused(False);  Module.SetAmplification(0.6);  Module.SetStereoSeparation(20);   PT_Audio_Init;  Module.Play(0, 0); end; procedure TForm1.OpenGLControl1Paint(Sender: TObject);var  ww, hh  : Integer;begin  ww := OpenGLControl1.Width;  hh := OpenGLControl1.Height;   glFillScreen(OpenGLControl1, 0.0, 0.0, 0.0, 1.0);   glSeascapeShader(0,0,ww,hh,tmr*2.0,0.0,0.0,2.0);  glDrawTexture2D(0,320,ww,tex_h*1.5,tex,2.0,2.0,0.0);  glBitmapFontText(fntx, 2500 - txtPosX, 160, s_txt, 36,38, 10,                1.0, 0.0, bmAlpha, 10.0, 12.0);   OpenGLControl1.SwapBuffers;end; procedure TForm1.Timer1Timer(Sender: TObject);begin  tmr := tmr +0.02;  txtPosX := txtPosX + 10; if txtPosX > 80000 then txtPosX := 0;   OpenGLControl1.Invalidate;end; procedure TForm1.FormDestroy(Sender: TObject);begin  if Module <> nil then Module.Stop;  PT_Audio_Close;  if Assigned(Module) then FreeAndNil(Module);end; end. ---------------------------------------------------------------------- Gigatron · 2026-06-02 10:46 Hi In addition you can see the live version of ascii shader demo on YT; used chars :' LAZARUSFPC' Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i glScreenAsciiShader(OpenGLControl1,12.0,12.0,1,1.0); procedure glScreenAsciiShader(glc: TOpenGLControl; char_w : Single = 8.0; char_h : Single = 8.0; colored : Integer = 1; intensity: Single = 1.0);  The weather here has gone completely crazy; storm here https://www.youtube.com/watch?v=PrefF7EpzRM Regards ---------------------------------------------------------------------- microxa · 2026-06-03 09:29 Great job, Gigatron! My old 9600GT is pushing through with all its might to handle these waves!Well, I tried to wrap my head around some of the basics using a lighter shader (one that actually runs on old integrated ATI chips), based on the "Ocean" sample from https://github .com/glscene/GLXEngine/tree/master/Examples/Demos/glslshadersTo do this, I needed to switch to a more lightweight framework, GLUT. Gemini helped me put the program together (and looking at it now, I realize I understand absolutely nothing about how it works). Anyway, at least it boots up and renders an image, even if it's still a bit far from the original look.Best of luck to everyone, and happy coding! ---------------------------------------------------------------------- microxa · 2026-06-06 05:03 Well, something interesting turned up for the ancient ATI — the Julia fractal. I didn’t even expect it to pull that off (20 iterations — that’s a record!). I had to push Gemini to find some simple and optimized solutions. Best Regards! Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i {$apptype console}program julia_fractal; uses GL, GLU, GLEXT, Glut; var  ShaderProgram,TextureID: GLuint;   // Julia C const  Cx: Single = -0.7;  Cy: Single = 0.27015;  Zoom: Single = 3.0; VertSrc:PChar =  'varying vec2 vTexCoord;'#10+  'void main() {'#10+      'vTexCoord = gl_MultiTexCoord0.xy;'#10+      'gl_Position = ftransform();'#10+  '}'#10; FragSrc:PChar=  'varying vec2 vTexCoord;'#10+  'uniform vec2 u_center;'#10+  'uniform float u_zoom,u_cx,u_cy;'#10+  'uniform sampler2D u_pal;'#10+  'void main() {'#10+      'float x = (vTexCoord.x - 0.5) * u_zoom;'#10+      'float y = (vTexCoord.y - 0.5) * u_zoom;'#10+      'for (int i = 0; i < 20; i++) {'#10+       //PLAZMA CUB: (x * x) + (y * y)           'float t = (x * x) - (y * y) + u_cx;'#10+          'y =  (x + x) * y + u_cy;'#10+          'x = t;'#10+      '}'#10+       'gl_FragColor = texture2D(u_pal, vec2(x, y) * 0.5 + vec2(0.5, 0.5));'#10+  '}'; procedure GenTexture;var  TextureData: array[0..255, 0..2] of Byte;  i: Integer;begin  randomize;   for i := 0 to 255 do  begin    TextureData[i, 0] := random(255);    TextureData[i, 1] := random(255);    TextureData[i, 2] := random(255);  end;   glGenTextures(1, @TextureID);   glBindTexture(GL_TEXTURE_2D, TextureID);   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);   glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 256, 1, 0, GL_RGB, GL_UNSIGNED_BYTE, @TextureData);   glBindTexture(GL_TEXTURE_2D, 0);end; procedure InitShaders;var  VertShader, FragShader: GLuint;  Compiled, Linked: GLint;begin  VertShader := glCreateShader(GL_VERTEX_SHADER);  glShaderSource(VertShader, 1, @VertSrc, nil);  glCompileShader(VertShader);   glGetShaderiv(VertShader, GL_COMPILE_STATUS, @Compiled);  if Compiled = GL_FALSE then Halt(1);   FragShader := glCreateShader(GL_FRAGMENT_SHADER);  glShaderSource(FragShader, 1, @FragSrc, nil);  glCompileShader(FragShader);   glGetShaderiv(FragShader, GL_COMPILE_STATUS, @Compiled);  if Compiled = GL_FALSE then Halt(1);   ShaderProgram := glCreateProgram();  glAttachShader(ShaderProgram, VertShader);  glAttachShader(ShaderProgram, FragShader);  glLinkProgram(ShaderProgram);   glGetProgramiv(ShaderProgram, GL_LINK_STATUS, @Linked);  if Linked = GL_FALSE then Halt(1);   glDeleteShader(VertShader);  glDeleteShader(FragShader);   glUseProgram(ShaderProgram);end; procedure DisplayProc; cdecl;var  LocZoom,LocCx,LocCy,LocPalette: GLint;begin   LocCx      := glGetUniformLocation(ShaderProgram, 'u_cx');  LocCy      := glGetUniformLocation(ShaderProgram, 'u_cy');  LocZoom    := glGetUniformLocation(ShaderProgram, 'u_zoom');   glUniform1f(LocZoom, Zoom);  glUniform1f(LocCx, Cx);  glUniform1f(LocCy, Cy);   glActiveTexture(GL_TEXTURE0);  glBindTexture(GL_TEXTURE_2D, TextureID);  LocPalette := glGetUniformLocation(ShaderProgram, 'u_pal');  glUniform1i(LocPalette, 0);   glBegin(GL_QUADS);    glMultiTexCoord2f(GL_TEXTURE0, 0.0, 0.0); glVertex2f(-1.0, -1.0);    glMultiTexCoord2f(GL_TEXTURE0, 1.0, 0.0); glVertex2f( 1.0, -1.0);    glMultiTexCoord2f(GL_TEXTURE0, 1.0, 1.0); glVertex2f( 1.0,  1.0);    glMultiTexCoord2f(GL_TEXTURE0, 0.0, 1.0); glVertex2f(-1.0,  1.0);  glEnd();   glutSwapBuffers();end; procedure ReshapeProc(w, h: Integer); cdecl;begin  glViewport(0, 0, w, h);end; procedure PassiveMotionProc(x, y: Integer); cdecl;begin  Cx := (x / glutGet(GLUT_WINDOW_WIDTH)) * 2.0 - 1.0;  Cy := (y / glutGet(GLUT_WINDOW_HEIGHT)) * 2.0 - 1.0;  glutPostRedisplay();end; procedure KeyboardProc(key: Byte; x, y: Integer); cdecl;begin  case Chr(key) of    '+', '=': Zoom := Zoom * 0.85;    '-':      Zoom := Zoom * 1.15;    'r','R':  GenTexture;    #27:      Halt(0);  end;  glutPostRedisplay();end; begin  glutInit(@argc, argv);  glutInitDisplayMode(GLUT_DOUBLE or GLUT_RGB or GLUT_DEPTH);  glutInitWindowSize(512, 512);  glutCreateWindow('Julia Set OpenGL 2.0');  glext_LoadExtension('GL_version_2_0');   glutDisplayFunc(@DisplayProc);  glutReshapeFunc(@ReshapeProc);  glutKeyboardFunc(@KeyboardProc);  glutPassiveMotionFunc(@PassiveMotionProc);   InitShaders; GenTexture;   glClearColor(0.0, 0.0, 0.0, 1.0);  glutMainLoop();end. ---------------------------------------------------------------------- Gigatron · 2026-06-12 23:48 Hi I am late and installed   lazarus 4.8 ; so here is the same fractal made with glcanvas with internal command : glDrawTexturedShader(0,0,ww,hh,tex,fs,1.0,1.0,1.0,1.0,0.0);  //  All project is packed to maintain demo style example with music; Feel free to play with formula in memo1 shader text.* Regards Gigatron ---------------------------------------------------------------------- microxa · 2026-06-14 10:37 Gigatron, thanks, my vintage laptop pulled off the demo! Though I had to figure out what was wrong this time; turned out it didn’t like a trailing ';', probably not by strict C canons. Respect for to do this! ---------------------------------------------------------------------- Gigatron · 2026-06-14 14:57 Hi Is possible Mac or old drivers are not accept directly the out color like this ; gl_FragColor =texture2D(u_texture,vec2(x, y) * 0.5 + vec2(0.5, 0.5)); But need to declare gl_FragColor correctly , so the out_color is vec4 variable (x,y,z,w) ; try this :  gl_FragColor = vec4(texture2D(u_texture,vec2(x, y) * 0.5 + vec2(0.5, 0.5),1.0)); missing 'w' was now set; Regards Gigatron Ps: When i am rich i will send you the latest and better laptop ---------------------------------------------------------------------- backprop · 2026-06-23 14:59 Hi Gigatron. What about Mandelbrot explorer with GLSL? Julia is just 2D, while Mandelbrot is full 4D. Or even more interesting - 3D cut instead standard 2D... IIRC, there is some fractal explorer which doing exactly that... At least it is more interesting to dig in that... ---------------------------------------------------------------------- Gigatron · 2026-06-23 17:10 Hi backprop Are you talking about this example ? https://mandelbrot.site/ Regards ---------------------------------------------------------------------- backprop · 2026-06-24 06:13 No. I have forgot what was it, but there was in the past projects which aimed fractals and not focusing just on 2D cut. ---------------------------------------------------------------------- MathMan · 2026-06-25 19:31 Quote from: backprop on June 24, 2026, 08:13:53 amNo. I have forgot what was it, but there was in the past projects which aimed fractals and not focusing just on 2D cut. Quaternion fractals maybe? For Julia type look here https://paulbourke.net/fractals/quatjulia/ ---------------------------------------------------------------------- backprop · 2026-06-25 20:30 Quote from: MathMan on June 25, 2026, 09:31:50 pmQuaternion fractals maybe? For Julia type look here https://paulbourke.net/fractals/quatjulia/ Right, something as this: https://icefractal.com/ And this is amazing structure, who would say this is just a fractal? https://paulbourke.net/fractals/midjourney/ ---------------------------------------------------------------------- microxa · 2026-06-25 21:46 This is the most cyberpunk craziness I've ever had to deal with on 16/8-bit machines. Gemini surprised me yet again with its proficiency in OpenGL, implementing (after roughly five attempts) a pixel-perfect OpenGL scroll for this "loom of integral randomness Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i  {$APPTYPE CONSOLE}{$mode objfpc}program OpenGLFractal_OnePixelScroll; uses  SysUtils,  GL,GLExt,Glu,Glut; //Fast random, origin from BK-0010 (PDP-11 community)//rework to Pascal by Gemini AIvar Seed: Integer = 1;function Rand(v: Integer): Integer;var  a, e: Integer;begin  a := seed;  e := byte(a) shr 1;  a := (a and $FFFFFF00 shl 1) or (a and 1 shl 8);  e := e xor (a shr 24);  Result := a xor e;  seed := Result;end; exports rand; const  TEX_WIDTH  = 1024;  TEX_HEIGHT = 512; var  TextureID: GLuint;   //All coordinates in integer  CurX: Integer = 0;  CurY: Integer = 0;  FineScroll: Integer = 0; // Shift to 0..1023   LineBuffer: array[0..8 * TEX_HEIGHT * 3 - 1] of GLubyte;   // mouse  RotX: Single = -28.0;// -34.50;  //45.0;  RotZ: Single = 90.0;  Zoom: Single = -1.2;//-2.5;  MouseX, MouseY: Integer;  MouseButton: Integer = -1;  // Write byte in vertical lineprocedure BufferByte(Y, Val: Integer);var  BitIdx, PixelOffset: Integer;  Color: integer;begin  for BitIdx := 7 downto 0 do  begin    PixelOffset := (Y * 8 + (7 - BitIdx)) * 3;     if ((Val shr BitIdx) and 1) = 1 then    Color := 0 else Color := $FFFFFF;     LineBuffer[PixelOffset + 0] := Color;       // R    LineBuffer[PixelOffset + 1] := Color shr 8; // G    LineBuffer[PixelOffset + 2] := Color shr 16;// B  end;end; // Visualizer (from Speccy/Orion-128)procedure RenderLine;var  R: Integer;begin  R := Rand(0);  BufferByte(CurY, R);  Inc(CurY);   if CurY >= TEX_HEIGHT then // Vertical line complete  begin    CurY := 0;     glBindTexture(GL_TEXTURE_2D, TextureID);    // Drop 8-pixels block to current X coordinate CurX    glTexSubImage2D(GL_TEXTURE_2D, 0, CurX, 0, 8, TEX_HEIGHT, GL_RGB, GL_UNSIGNED_BYTE, @LineBuffer);   // Shift marker up 8 pixels    CurX := CurX + 8;    if CurX >= TEX_WIDTH then    begin      CurX := 0;    end;  end;end; procedure Idle; cdecl;var  i: Integer;begin   for i := 1 to (TEX_HEIGHT div 8) do RenderLine;   FineScroll := FineScroll + 1;   if FineScroll >= TEX_WIDTH then    FineScroll := FineScroll - TEX_WIDTH;   glutPostRedisplay;end; procedure Display; cdecl;var  NormOffset: Single;begin  glClear(GL_COLOR_BUFFER_BIT or GL_DEPTH_BUFFER_BIT);   NormOffset := ((FineScroll + 8) / TEX_WIDTH);   glMatrixMode(GL_TEXTURE);  glLoadIdentity;  glTranslatef(NormOffset, 0.0, 0.0); // Shift one pixel   // --- ������� ������ (3D) ---  glMatrixMode(GL_MODELVIEW);  glLoadIdentity;   glTranslatef(0.0, 0.0, Zoom);  glRotatef(RotX, 1.0, 0.0, 0.0);  glRotatef(RotZ, 0.0, 0.0, 1.0);   glBindTexture(GL_TEXTURE_2D, TextureID);  glBegin(GL_QUADS);  glTexCoord2f(0.0, 0.0); glVertex3f(-1.5, -0.75, 0.0);    glTexCoord2f(1.0, 0.0); glVertex3f( 1.5, -0.75, 0.0);    glTexCoord2f(1.0, 1.0); glVertex3f( 1.5,  0.75, 0.0);    glTexCoord2f(0.0, 1.0); glVertex3f(-1.5,  0.75, 0.0);  glEnd;   Sleep(40);  glutSwapBuffers;end; procedure Reshape(Width, Height: Integer); cdecl;begin  if Height = 0 then Height := 1;  glViewport(0, 0, Width, Height);  glMatrixMode(GL_PROJECTION);  glLoadIdentity;  gluPerspective(45.0, Width / Height, 0.1, 100.0);  glMatrixMode(GL_MODELVIEW);end; procedure Mouse(button, state, x, y: Integer); cdecl;begin  if state = GLUT_DOWN then  begin    MouseButton := button; MouseX := x; MouseY := y;  end else MouseButton := -1;end; procedure Motion(x, y: Integer); cdecl;begin  if MouseButton = GLUT_LEFT_BUTTON then  begin    RotZ := RotZ + (x - MouseX) * 0.5;    RotX := RotX + (y - MouseY) * 0.5;    MouseX := x; MouseY := y; glutPostRedisplay;   end;  if MouseButton = GLUT_RIGHT_BUTTON then  begin    Zoom := Zoom + (y - MouseY) * 0.01; MouseY := y; glutPostRedisplay;  end;end; procedure Init; var i:integer;begin  glClearColor(0.0, 0.0, 0.0, 1.0);  glEnable(GL_TEXTURE_2D);  glEnable(GL_DEPTH_TEST);   glGenTextures(1, @TextureID);  glBindTexture(GL_TEXTURE_2D, TextureID);   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);//GL_NEAREST);  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);//GL_NEAREST);   glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, TEX_WIDTH, TEX_HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, nil);   for i := 1 to (TEX_WIDTH * TEX_HEIGHT) div 8 do RenderLine; end;  begin  glutInit(@argc, argv);  glutInitDisplayMode(GLUT_DOUBLE or GLUT_RGB or GLUT_DEPTH);  glutInitWindowSize(1024, 600);  glutCreateWindow('XORSHIFT 1-Pixel Scroll');   Init;   glutReshapeFunc(@Reshape);  glutDisplayFunc(@Display);  glutIdleFunc(@Idle);  glutMouseFunc(@Mouse);  glutMotionFunc(@Motion);   glutMainLoop;end. ---------------------------------------------------------------------- Gigatron · 2026-07-29 22:42 Hi In the past i've made a nice game for construct2 called X-ball, this attempt is try to make this game in pascal code using glCanvas; https://www.construct.net/en/free-online-games/x-ball-1727/play Please improve or play with it; Arrow keys Left/Right to control ball and hit 'S' Sprite to gain speed . Regards Gigatron ---------------------------------------------------------------------- Datalore · 2026-07-30 21:25 Looks like a neat fun little game  Just a tiny nitpick, glLoadPNGToTexture('fonts/32/bitmap_font.png', fntx_w, fntx_h); should really, really, really be glLoadPNGToTexture('Fonts/32/bitmap_font.png', fntx_w, fntx_h); as the name of your fonts directory is capitalized. Things tend to be case sensitive on some systems ;-) Granted, code from Redmond is designed by clowns who are supervised by monkeys who report to caffeinated toddlers who are overseen by a bunch of floppy puppies who are monitored by a wasted bachelorette party whose boss is just a large inflatable tube man (take this with a large grain of salt, i'm not really serious here) so on most of these systems this doesn't matter as much, but it can be enabled. ---------------------------------------------------------------------- Gigatron · 2026-08-06 23:53 @Datalore  it's ok for future; Today i would share something new with lazarus users, i am working on a new oldschool demomaker library only for windows like fastcanvas with Win Api but this time GL rendering and LCL free, just made a little demo; the exec is very small than 300 kb; Sfx  : by Reptile & Sky ; outrun 2000 remix . xm zipped; Regards  GTR ---------------------------------------------------------------------- microxa · 2026-08-09 11:11 An AI-slop WinAPI implementation of the legacy GLUT ---------------------------------------------------------------------- Thausand · 2026-08-09 15:25 Quote from: microxa on August 09, 2026, 01:11:53 pmAn AI-slop WinAPI implementation of the legacy GLUT Is exist https://gitlab.com/freepascal.org/fpc/source/- /blob/main/packages/opengl/src/glut.pp?ref_type=heads (not sure for version you make) ---------------------------------------------------------------------- Gigatron · 2026-08-09 23:28 Hi 2D primitives added with xmp player lite version (no packing added) this mean the module must not zipped. Cool demo example here ; Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-08-21 23:39 Hello;  I'm working on 5 Java projects with Android Studio so I'm not there yet, but of course I'm doing oldschool demos in my little free time with the glCanvas101... Here is the remake of the second demo after Boing Ball... El Gato (Blair· Sullivan Computer Graphics, 1987) Cat animation demo... live version on YT; https://www.youtube.com/watch?v=wKmHqsX4vZE Original: https://www.youtube.com/watch?v=hNT4w8DLEaI Sfx sample by; Depeche Mode - Strangelove (Razormaid Mix) https://www.youtube.com/watch?v=F2aR2-53jRE All size calculated to 500 kb to upload to the forum , modules and other gfx , sorry for bad resolution. Regards Gigatron ---------------------------------------------------------------------- Gigatron · 2026-08-26 23:35 Hi I would like to share a new demo coded with the latest glcanvas 1.01 added some new fx to make the Famous World of Wondes copper cycle command ;  --  glCopperCycle(0, 0, ww, scaleY, WoWRamps, 31, 10, 10, 38, tmr*4.0); WowRamps are colors of bands like so ; WoWRamps: array[0..6] of TglColor = (     (R:0; G:0; B:1; A:1),   // bleu     (R:0; G:1; B:0; A:1),   // vert     (R:1; G:0; B:0; A:1),   // rouge     (R:1; G:0; B:1; A:1),   // magenta     (R:0; G:1; B:1; A:1),   // cyan     (R:1; G:1; B:0; A:1),   // jaune     (R:1; G:1; B:1; A:1)    // blanc   );  Wow demo on YT ; https://www.youtube.com/watch?v=EQe7WycyYwE  My demo on YT  ; https://www.youtube.com/watch?v=fZJCAivXI8U Contain old amiga digitized sound from various group .. (1986-87) before Soundracker; Demo zipped in one file; with just 1 digitized sample Regards