Browse Source

* FloodFill: did not take into account current viewport settings
* GetScanLine: only get line inside viewport, data outside of it
is not used anyway
* InternalEllipseDefault: fix for when xradius or yradius = 0 and
increase xradius and yradius always by one (TP does this too)
* fixed conlict in vesa.inc from last update
* some conditionals to avoid range check and overflow errors in
places where it doesn't matter

Jonas Maebe 26 years ago
parent
commit
cb55fd4de2
4 changed files with 142 additions and 67 deletions
  1. 25 11
      rtl/inc/graph/fills.inc
  2. 63 9
      rtl/inc/graph/graph.inc
  3. 43 23
      rtl/inc/graph/graph.pp
  4. 11 24
      rtl/inc/graph/vesa.inc

+ 25 - 11
rtl/inc/graph/fills.inc

@@ -418,20 +418,24 @@ var
    BackupColor : Word;
    x1, x2: integer;
    Index : Integer;
+{ !!! }
+   allocated: longint;
   Begin
     { Save current drawing color }
     BackupColor := CurrentColor;
     CurrentColor := FillSettings.Color;
     { MaxX is based on zero index }
-    GetMem (s1,(MaxX+1)*2);  { A pixel color represents a word }
-    GetMem (s2,(MaxX+1)*2);  { A pixel color represents a word }
-    GetMem (s3,(MaxX+1)*2);  { A pixel color represents a word }
+    allocated := (ViewWidth+1)*2;
+    GetMem (s1,(ViewWidth+1)*2);  { A pixel color represents a word }
+    GetMem (s2,(ViewWidth+1)*2);  { A pixel color represents a word }
+    GetMem (s3,(ViewWidth+1)*2);  { A pixel color represents a word }
     if (not assigned(s1)) or (not assigned(s2)) or (not assigned(s3)) then
       begin
         _GraphResult := grNoFloodMem;
         exit;
       end;
-    If (x<0) Or (y<0) Or (x>MaxX) Or (y>MaxY) then Exit;
+    If (x<0) Or (y<0) Or
+       (x>ViewWidth) Or (y>ViewHeight) then Exit;
     { Some internal variables }
     Index := 0;
     { Index of segments to draw }
@@ -448,14 +452,14 @@ var
        GetScanline (y+1,s3^);
 
        { check the current scan line }
-       While (s1^[x]<>Border) And (x<=MaxX) Do Inc (x);
+       While (s1^[x]<>Border) And (x<ViewWidth) Do Inc (x);
        d:=0;
        e:=0;
-       Dec (x);
+       dec(x);
        Beginx:=x;
        REPEAT
          { check the above line }
-         If y<MaxY then
+         If y<ViewHeight then
            Begin
               Cont:=(s3^[x]<>Border) and (not AlreadyDrawn(x,y+1));
               If (e=0) And Cont then
@@ -494,15 +498,25 @@ var
        PatternLine (x1,x2,y);
      End; { end while }
 
-    FreeMem (s1,(MaxX+1)*2);
-    FreeMem (s2,(MaxX+1)*2);
-    FreeMem (s3,(MaxX+1)*2);
+    FreeMem (s1,(ViewWidth+1)*2);
+    FreeMem (s2,(ViewWidth+1)*2);
+    FreeMem (s3,(ViewWidth+1)*2);
     CurrentColor := BackUpColor;
   End;
 
 {
 $Log$
-Revision 1.4  1999-07-12 14:52:52  jonas
+Revision 1.5  1999-09-11 19:43:00  jonas
+  * FloodFill: did not take into account current viewport settings
+  * GetScanLine: only get line inside viewport, data outside of it
+    is not used anyway
+  * InternalEllipseDefault: fix for when xradius or yradius = 0 and
+    increase xradius and yradius always by one (TP does this too)
+  * fixed conlict in vesa.inc from last update
+  * some conditionals to avoid range check and overflow errors in
+    places where it doesn't matter
+
+Revision 1.4  1999/07/12 14:52:52  jonas
   * fixed procvar syntax error and ceil and floor functions
 
 Revision 1.3  1999/07/12 13:27:11  jonas

+ 63 - 9
rtl/inc/graph/graph.inc

@@ -119,7 +119,7 @@ CONST
   var
      ScrWidth : word absolute $40:$4a;
 
-
+{$ifndef tp}
   procedure seg_bytemove(sseg : word;source : longint;dseg : word;dest : longint;count : longint);
 
     begin
@@ -139,6 +139,7 @@ CONST
           pop es
        end ['ESI','EDI','ECX','EAX']
     end;
+{$endif tp}
 
  {************************************************************************}
  {*                     4-bit planar VGA mode routines                   *}
@@ -587,6 +588,7 @@ CONST
 {$endif asmgraph}
  end;
 
+{$ifndef tp}
   procedure HLine16(x,x2,y: integer); far;
 
    var
@@ -641,8 +643,23 @@ CONST
 
     port[$3ce]:=8;
     port[$3cf]:=LMask;
+{$ifopt r+}
+{$define rangeOn}
+{$r-}
+{$endif}
+{$ifopt q+}
+{$define overflowOn}
+{$q-}
+{$endif}
     Mem[$a000:ScrOfs]:=Mem[$a000:ScrOfs]+1;
-
+{$ifdef rangeOn}
+{$undef rangeOn}
+{$r+}
+{$endif}
+{$ifdef overflowOn}
+{$undef overflowOn}
+{$q+}
+{$endif}
     port[$3ce]:=8;
     if HLength>0 then
       begin
@@ -655,7 +672,23 @@ CONST
               ScrOfs:=ScrOfs+HLength;
            end;
          port[$3cf]:=RMask;
+{$ifopt r+}
+{$define rangeOn}
+{$r-}
+{$endif}
+{$ifopt q+}
+{$define overflowOn}
+{$q-}
+{$endif}
          Mem[$a000:ScrOfs]:=Mem[$a000:ScrOfs]+1;
+{$ifdef rangeOn}
+{$undef rangeOn}
+{$r+}
+{$endif}
+{$ifdef overflowOn}
+{$undef overflowOn}
+{$q+}
+{$endif}
       end;
     // clean up
     port[$3cf]:=0;
@@ -717,7 +750,23 @@ CONST
     end;
     for i:=y to y2 do
       begin
+{$ifopt r+}
+{$define rangeOn}
+{$r-}
+{$endif}
+{$ifopt q+}
+{$define overflowOn}
+{$q-}
+{$endif}
          Mem[$a000:ScrOfs]:=Mem[$a000:ScrOfs]+1;
+{$ifdef rangeOn}
+{$undef rangeOn}
+{$r+}
+{$endif}
+{$ifdef overflowOn}
+{$undef overflowOn}
+{$q+}
+{$endif}
          ScrOfs:=ScrOfs+ScrWidth;
       end;
     // clean up
@@ -729,6 +778,7 @@ CONST
     port[$3ce]:=3;
     port[$3cf]:=0;
   End;
+{$endif tp}
 
 
  procedure SetVisual480(page: word); far;
@@ -1741,8 +1791,6 @@ const CrtAddress: word = 0;
          mode.SetVisualPage := SetVisual200;
          mode.SetActivePage := SetActive200;
          mode.InitMode := Init640x200x16;
-         mode.HLine := HLine16;
-         mode.VLine := VLine16;
 {$else fpc}
          mode.DirectPutPixel:=@DirectPutPixel16;
          mode.PutPixel:=@PutPixel16;
@@ -1778,8 +1826,6 @@ const CrtAddress: word = 0;
          mode.GetRGBPalette := GetVGARGBPalette;
          mode.SetVisualPage := SetVisual350;
          mode.SetActivePage := SetActive350;
-         mode.HLine := HLine16;
-         mode.VLine := VLine16;
 {$else fpc}
          mode.DirectPutPixel:=@DirectPutPixel16;
          mode.PutPixel:=@PutPixel16;
@@ -1815,8 +1861,6 @@ const CrtAddress: word = 0;
          mode.InitMode := Init640x480x16;
          mode.SetVisualPage := SetVisual480;
          mode.SetActivePage := SetActive480;
-         mode.HLine := HLine16;
-         mode.VLine := VLine16;
 {$else fpc}
          mode.DirectPutPixel:=@DirectPutPixel16;
          mode.PutPixel:=@PutPixel16;
@@ -2519,7 +2563,17 @@ const CrtAddress: word = 0;
 
 {
 $Log$
-Revision 1.9  1999-08-01 14:50:51  jonas
+Revision 1.10  1999-09-11 19:43:01  jonas
+  * FloodFill: did not take into account current viewport settings
+  * GetScanLine: only get line inside viewport, data outside of it
+    is not used anyway
+  * InternalEllipseDefault: fix for when xradius or yradius = 0 and
+    increase xradius and yradius always by one (TP does this too)
+  * fixed conlict in vesa.inc from last update
+  * some conditionals to avoid range check and overflow errors in
+    places where it doesn't matter
+
+Revision 1.9  1999/08/01 14:50:51  jonas
   * fixed hline16 and vline16 for notput (also TP supports copy, and, or, xor and
     notput for lines!!)
   * fixed directputpixel16 to support all the different put types

+ 43 - 23
rtl/inc/graph/graph.pp

@@ -699,7 +699,7 @@ const
 type
 
 
-  tinttable = array[0..8192] of integer;
+  tinttable = array[0..16383] of integer;
   pinttable = ^tinttable;
 
   WordArray = Array [0..StdbufferSize] Of word;
@@ -927,7 +927,8 @@ var
      {******************************************}
      {  SLOPED SOLID LINES                      }
      {******************************************}
-           oldCurrentColor := CurrentColor;
+           oldCurrentColor :=
+           CurrentColor;
            { Calculate deltax and deltay for initialisation }
            deltax := abs(x2 - x1);
            deltay := abs(y2 - y1);
@@ -1294,6 +1295,10 @@ var
     TmpAngle: word;
     DeltaAngle: word;
   Begin
+   If xradius = 0 then inc(x);
+   if yradius = 0 then inc(y);
+   inc(xradius);
+   inc(yradius);
    { check if valid angles }
    stangle := stAngle mod 361;
    EndAngle := EndAngle mod 361;
@@ -1311,7 +1316,7 @@ var
      Begin
        { approximate the number of pixels required by using the circumference }
        { equation of an ellipse.                                              }
-       NumOfPixels:=8*Round(2*sqrt((sqr(XRadius)+sqr(YRadius)) div 2));
+       NumOfPixels:=8*Round(2.5*sqrt((sqr(XRadius)+sqr(YRadius)) div 2));
        GetMem(xpt,NumOfpixels*sizeof(word));
        GetMem(ypt,NumOfPixels*sizeof(word));
        { Calculate the angle precision required }
@@ -1339,9 +1344,9 @@ var
    {  CIRCLE OR ELLIPSE WITH THICKNESS=3      }
    {******************************************}
     Begin
-      NumOfPix[1]:=8*Round(2*sqrt((sqr(XRadius)+sqr(YRadius)) div 2));
-      NumOfPix[0]:=8*Round(2*sqrt((sqr(XRadius-1)+sqr(YRadius-1)) div 2));
-      NumOfPix[2]:=8*Round(2*sqrt((sqr(XRadius+1)+sqr(YRadius+1)) div 2));
+      NumOfPix[1]:=8*Round(2.5*sqrt((sqr(XRadius)+sqr(YRadius)) div 2));
+      NumOfPix[0]:=8*Round(2.5*sqrt((sqr(XRadius-1)+sqr(YRadius-1)) div 2));
+      NumOfPix[2]:=8*Round(2.5*sqrt((sqr(XRadius+1)+sqr(YRadius+1)) div 2));
       GetMem(xpt,(NumOfPix[1]+NumOfPix[2]+NumOfPix[0])*sizeof(word));
       GetMem(ypt,(NumOfPix[1]+NumOfPix[2]+NumOfPix[0])*sizeof(word));
       { removed from inner loop to make faster }
@@ -1551,7 +1556,7 @@ End;
      CurrentWriteMode := NormalPut;
 
      { number of times to go throuh the 8x8 pattern }
-     NrIterations := abs(x2 - x1) div 8;
+     NrIterations := abs(x2 - x1+1) div 8;
      Inc(NrIterations);
 
 
@@ -1564,13 +1569,15 @@ End;
        begin
          OldCurrentColor := CurrentColor;
          CurrentColor := CurrentBkColor;
-         HLine(x1,x2,y);
+{ hline converts the coordinates to global ones, but that has been done }
+{ already here!!! Convert them bak to local ones... (JM)                }
+         HLine(x1-StartXViewPort,x2-StartXViewPort,y-StartYViewPort);
          CurrentColor := OldCurrentColor;
        end
      else
      if  FillSettings.Pattern = SolidFill then
        begin
-         HLine(x1,x2,y);
+         HLine(x1-StartXViewPort,x2-StartXViewPort,y-StartYViewPort);
        end
      else
        begin
@@ -1665,15 +1672,15 @@ End;
             CenterLn: LineInfo.Pattern :=  $FC78;   { -- - -- }
        end; { end case }
        { setup pattern styles }
-       j:=15;
+       j:=16;
        for i:=0 to 15 do
         Begin
+         dec(j);
          { bitwise mask for each bit in the word }
          if (word($01 shl i) AND LineInfo.Pattern) <> 0 then
                LinePatterns[j]:=TRUE
              else
                LinePatterns[j]:=FALSE;
-             Dec(j);
         end;
       end;
    end;
@@ -1787,19 +1794,21 @@ end;
 
 
   Procedure GetScanlineDefault (Y : Integer; Var Data); far;
-  {********************************************************}
-  { Procedure GetScanLine()                                }
-  {--------------------------------------------------------}
-  { Returns the full scanline of the video line of the Y   }
-  { coordinate. The values are returned in a WORD array    }
-  { each WORD representing a pixel of the specified scanline}
-  {********************************************************}
+  {**********************************************************}
+  { Procedure GetScanLine()                                  }
+  {----------------------------------------------------------}
+  { Returns the full scanline of the video line of the Y     }
+  { coordinate. The values are returned in a WORD array      }
+  { each WORD representing a pixel of the specified scanline }
+  { note: we only need the pixels inside the ViewPort! (JM)  }
+  {**********************************************************}
+
 
   Var
-    Offset, x : Integer;
+    x : Integer;
   Begin
-     For x:=0 to MaxX Do Begin
-            WordArray(Data)[x]:=GetPixel(x, y);
+     For x:=0 to ViewWidth Do Begin
+       WordArray(Data)[x]:=GetPixel(x, y);
      End;
   End;
 
@@ -2062,7 +2071,8 @@ end;
     OldWriteMode := CurrentWriteMode;
     CurrentWriteMode := NormalPut;
     InternalEllipse(X,Y,XRadius,YRadius,0,360);
-    FloodFill(X,Y,CurrentColor);
+    if (XRadius > 0) and (YRadius > 0) then
+      FloodFill(X,Y,CurrentColor);
     { restore old write mode }
     CurrentWriteMode := OldWriteMode;
   end;
@@ -2680,7 +2690,17 @@ DetectGraph
 
 {
   $Log$
-  Revision 1.18  1999-07-26 09:38:41  florian
+  Revision 1.19  1999-09-11 19:43:01  jonas
+    * FloodFill: did not take into account current viewport settings
+    * GetScanLine: only get line inside viewport, data outside of it
+      is not used anyway
+    * InternalEllipseDefault: fix for when xradius or yradius = 0 and
+      increase xradius and yradius always by one (TP does this too)
+    * fixed conlict in vesa.inc from last update
+    * some conditionals to avoid range check and overflow errors in
+      places where it doesn't matter
+
+  Revision 1.18  1999/07/26 09:38:41  florian
     * bar: y2 can be less y1, fixed
     * settextstyle: charsize can be 0, must be changed into 1
 

+ 11 - 24
rtl/inc/graph/vesa.inc

@@ -481,7 +481,6 @@ end;
   begin
      offs := longint(y) * BytesPerLine + x;
      SetWriteBank(integer(offs shr 16));
-<<<<<<< vesa.inc
      Case CurrentWriteMode of
        XorPut:
          Begin
@@ -502,28 +501,6 @@ end;
          mem[WinWriteSeg : word(offs)] := byte(currentcolor)
       else mem[WinWriteSeg : word(offs)] := byte(CurrentColor);
    End;
-=======
-     Case CurrentWriteMode of
-       XorPut:
-         Begin
-           SetReadBank(integer(offs shr 16));
-           mem[WinWriteSeg : word(offs)] := mem[WinReadSeg : word(offs)] xor byte(CurrentColor);
-         End;
-       AndPut:
-         Begin
-           SetReadBank(integer(offs shr 16));
-           mem[WinWriteSeg : word(offs)] := mem[WinReadSeg : word(offs)] And byte(CurrentColor);
-         End;
-       OrPut:
-         Begin
-           SetReadBank(integer(offs shr 16));
-           mem[WinWriteSeg : word(offs)] := mem[WinReadSeg : word(offs)] or byte(CurrentColor);
-         End;
-       NormalPut:
-         mem[WinWriteSeg : word(offs)] := byte(CurrentColor)
-     Else mem[WinWriteSeg : word(offs)] := byte(CurrentColor);
-   End;
->>>>>>> 1.8
   end;
 
   function GetPixVESA256(x, y : integer): word; far;
@@ -1484,7 +1461,17 @@ end;
 
 {
 $Log$
-Revision 1.9  1999-08-01 14:51:07  jonas
+Revision 1.10  1999-09-11 19:43:02  jonas
+  * FloodFill: did not take into account current viewport settings
+  * GetScanLine: only get line inside viewport, data outside of it
+    is not used anyway
+  * InternalEllipseDefault: fix for when xradius or yradius = 0 and
+    increase xradius and yradius always by one (TP does this too)
+  * fixed conlict in vesa.inc from last update
+  * some conditionals to avoid range check and overflow errors in
+    places where it doesn't matter
+
+Revision 1.9  1999/08/01 14:51:07  jonas
   * removed and/or/xorput support from vesaputpix256 (not in TP either)
   * added notput support to directputpix256