B
This commit is contained in:
parent
e5e8880e41
commit
518da4a923
1019 changed files with 15877 additions and 0 deletions
2
Task/Bitmap-Midpoint-circle-algorithm/0DESCRIPTION
Normal file
2
Task/Bitmap-Midpoint-circle-algorithm/0DESCRIPTION
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
Using the data storage type defined [[Basic_bitmap_storage|on this page]] for raster images, write an implementation of the '''midpoint circle algorithm''' (also known as '''Bresenham's circle algorithm'''). <BR>
|
||||
([[wp:Midpoint_circle_algorithm|definition on Wikipedia]]).
|
||||
2
Task/Bitmap-Midpoint-circle-algorithm/1META.yaml
Normal file
2
Task/Bitmap-Midpoint-circle-algorithm/1META.yaml
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
---
|
||||
note: Raster graphics operations
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
PRAGMAT READ "Basic_bitmap_storage.a68" PRAGMAT;
|
||||
|
||||
circle OF class image :=
|
||||
( REF IMAGE picture,
|
||||
POINT center,
|
||||
INT radius,
|
||||
PIXEL color
|
||||
)VOID:
|
||||
BEGIN
|
||||
INT f := 1 - radius,
|
||||
POINT ddf := (0, -2 * radius),
|
||||
df := (0, radius);
|
||||
picture [x OF center, y OF center + radius] :=
|
||||
picture [x OF center, y OF center - radius] :=
|
||||
picture [x OF center + radius, y OF center] :=
|
||||
picture [x OF center - radius, y OF center] := color;
|
||||
WHILE x OF df < y OF df DO
|
||||
IF f >= 0 THEN
|
||||
y OF df -:= 1;
|
||||
y OF ddf +:= 2;
|
||||
f +:= y OF ddf
|
||||
FI;
|
||||
x OF df +:= 1;
|
||||
x OF ddf +:= 2;
|
||||
f +:= x OF ddf + 1;
|
||||
picture [x OF center + x OF df, y OF center + y OF df] :=
|
||||
picture [x OF center - x OF df, y OF center + y OF df] :=
|
||||
picture [x OF center + x OF df, y OF center - y OF df] :=
|
||||
picture [x OF center - x OF df, y OF center - y OF df] :=
|
||||
picture [x OF center + y OF df, y OF center + x OF df] :=
|
||||
picture [x OF center - y OF df, y OF center + x OF df] :=
|
||||
picture [x OF center + y OF df, y OF center - x OF df] :=
|
||||
picture [x OF center - y OF df, y OF center - x OF df] := color
|
||||
OD
|
||||
END # circle #;
|
||||
|
||||
#
|
||||
The following illustrates use:
|
||||
#
|
||||
|
||||
IF test THEN
|
||||
REF IMAGE x = INIT LOC [1:16, 1:16] PIXEL;
|
||||
(fill OF class image)(x, (white OF class image));
|
||||
(circle OF class image)(x, (8, 8), 5, (black OF class image));
|
||||
(print OF class image)(x)
|
||||
FI
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
procedure Circle
|
||||
( Picture : in out Image;
|
||||
Center : Point;
|
||||
Radius : Natural;
|
||||
Color : Pixel
|
||||
) is
|
||||
F : Integer := 1 - Radius;
|
||||
ddF_X : Integer := 0;
|
||||
ddF_Y : Integer := -2 * Radius;
|
||||
X : Integer := 0;
|
||||
Y : Integer := Radius;
|
||||
begin
|
||||
Picture (Center.X, Center.Y + Radius) := Color;
|
||||
Picture (Center.X, Center.Y - Radius) := Color;
|
||||
Picture (Center.X + Radius, Center.Y) := Color;
|
||||
Picture (Center.X - Radius, Center.Y) := Color;
|
||||
while X < Y loop
|
||||
if F >= 0 then
|
||||
Y := Y - 1;
|
||||
ddF_Y := ddF_Y + 2;
|
||||
F := F + ddF_Y;
|
||||
end if;
|
||||
X := X + 1;
|
||||
ddF_X := ddF_X + 2;
|
||||
F := F + ddF_X + 1;
|
||||
Picture (Center.X + X, Center.Y + Y) := Color;
|
||||
Picture (Center.X - X, Center.Y + Y) := Color;
|
||||
Picture (Center.X + X, Center.Y - Y) := Color;
|
||||
Picture (Center.X - X, Center.Y - Y) := Color;
|
||||
Picture (Center.X + Y, Center.Y + X) := Color;
|
||||
Picture (Center.X - Y, Center.Y + X) := Color;
|
||||
Picture (Center.X + Y, Center.Y - X) := Color;
|
||||
Picture (Center.X - Y, Center.Y - X) := Color;
|
||||
end loop;
|
||||
end Circle;
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
X : Image (1..16, 1..16);
|
||||
begin
|
||||
Fill (X, White);
|
||||
Circle (X, (8, 8), 5, Black);
|
||||
Print (X);
|
||||
|
|
@ -0,0 +1,43 @@
|
|||
Width% = 200
|
||||
Height% = 200
|
||||
|
||||
REM Set window size:
|
||||
VDU 23,22,Width%;Height%;8,16,16,128
|
||||
|
||||
REM Draw circles:
|
||||
PROCcircle(100,100,40, 0,0,0)
|
||||
PROCcircle(100,100,80, 255,0,0)
|
||||
END
|
||||
|
||||
DEF PROCcircle(cx%,cy%,r%,R%,G%,B%)
|
||||
LOCAL f%, x%, y%, ddx%, ddy%
|
||||
f% = 1 - r% : y% = r% : ddy% = - 2*r%
|
||||
PROCsetpixel(cx%, cy%+r%, R%,G%,B%)
|
||||
PROCsetpixel(cx%, cy%-r%, R%,G%,B%)
|
||||
PROCsetpixel(cx%+r%, cy%, R%,G%,B%)
|
||||
PROCsetpixel(cx%-r%, cy%, R%,G%,B%)
|
||||
WHILE x% < y%
|
||||
IF f% >= 0 THEN
|
||||
y% -= 1
|
||||
ddy% += 2
|
||||
f% += ddy%
|
||||
ENDIF
|
||||
x% += 1
|
||||
ddx% += 2
|
||||
f% += ddx% + 1
|
||||
PROCsetpixel(cx%+x%, cy%+y%, R%,G%,B%)
|
||||
PROCsetpixel(cx%-x%, cy%+y%, R%,G%,B%)
|
||||
PROCsetpixel(cx%+x%, cy%-y%, R%,G%,B%)
|
||||
PROCsetpixel(cx%-x%, cy%-y%, R%,G%,B%)
|
||||
PROCsetpixel(cx%+y%, cy%+x%, R%,G%,B%)
|
||||
PROCsetpixel(cx%-y%, cy%+x%, R%,G%,B%)
|
||||
PROCsetpixel(cx%+y%, cy%-x%, R%,G%,B%)
|
||||
PROCsetpixel(cx%-y%, cy%-x%, R%,G%,B%)
|
||||
ENDWHILE
|
||||
ENDPROC
|
||||
|
||||
DEF PROCsetpixel(x%,y%,r%,g%,b%)
|
||||
COLOUR 1,r%,g%,b%
|
||||
GCOL 1
|
||||
LINE x%*2,y%*2,x%*2,y%*2
|
||||
ENDPROC
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
void raster_circle(
|
||||
image img,
|
||||
unsigned int x0,
|
||||
unsigned int y0,
|
||||
unsigned int radius,
|
||||
color_component r,
|
||||
color_component g,
|
||||
color_component b );
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
#define plot(x, y) put_pixel_clip(img, x, y, r, g, b)
|
||||
|
||||
void raster_circle(
|
||||
image img,
|
||||
unsigned int x0,
|
||||
unsigned int y0,
|
||||
unsigned int radius,
|
||||
color_component r,
|
||||
color_component g,
|
||||
color_component b )
|
||||
{
|
||||
int f = 1 - radius;
|
||||
int ddF_x = 0;
|
||||
int ddF_y = -2 * radius;
|
||||
int x = 0;
|
||||
int y = radius;
|
||||
|
||||
plot(x0, y0 + radius);
|
||||
plot(x0, y0 - radius);
|
||||
plot(x0 + radius, y0);
|
||||
plot(x0 - radius, y0);
|
||||
|
||||
while(x < y)
|
||||
{
|
||||
if(f >= 0)
|
||||
{
|
||||
y--;
|
||||
ddF_y += 2;
|
||||
f += ddF_y;
|
||||
}
|
||||
x++;
|
||||
ddF_x += 2;
|
||||
f += ddF_x + 1;
|
||||
plot(x0 + x, y0 + y);
|
||||
plot(x0 - x, y0 + y);
|
||||
plot(x0 + x, y0 - y);
|
||||
plot(x0 - x, y0 - y);
|
||||
plot(x0 + y, y0 + x);
|
||||
plot(x0 - y, y0 + x);
|
||||
plot(x0 + y, y0 - x);
|
||||
plot(x0 - y, y0 - x);
|
||||
}
|
||||
}
|
||||
#undef plot
|
||||
|
|
@ -0,0 +1,29 @@
|
|||
: circle { x y r color bmp -- }
|
||||
1 r - 0 r 2* negate 0 r { f ddx ddy dx dy }
|
||||
color x y r + bmp b!
|
||||
color x y r - bmp b!
|
||||
color x r + y bmp b!
|
||||
color x r - y bmp b!
|
||||
begin dx dy < while
|
||||
f 0< 0= if
|
||||
dy 1- to dy
|
||||
ddy 2 + dup to ddy
|
||||
f + to f
|
||||
then
|
||||
dx 1+ to dx
|
||||
ddx 2 + dup to ddx
|
||||
f 1+ + to f
|
||||
color x dx + y dy + bmp b!
|
||||
color x dx - y dy + bmp b!
|
||||
color x dx + y dy - bmp b!
|
||||
color x dx - y dy - bmp b!
|
||||
color x dy + y dx + bmp b!
|
||||
color x dy - y dx + bmp b!
|
||||
color x dy + y dx - bmp b!
|
||||
color x dy - y dx - bmp b!
|
||||
repeat ;
|
||||
|
||||
12 12 bitmap value test
|
||||
0 test bfill
|
||||
6 6 5 blue test circle
|
||||
test bshow cr
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
interface draw_circle
|
||||
module procedure draw_circle_sc, draw_circle_rgb
|
||||
end interface
|
||||
|
||||
private :: plot, draw_circle_toch
|
||||
|
|
@ -0,0 +1,74 @@
|
|||
subroutine plot(ch, p, v)
|
||||
integer, dimension(:,:), intent(out) :: ch
|
||||
type(point), intent(in) :: p
|
||||
integer, intent(in) :: v
|
||||
|
||||
integer :: cx, cy
|
||||
! I've kept the default 1-based array, but top-left corner pixel
|
||||
! is labelled as (0,0).
|
||||
cx = p%x + 1
|
||||
cy = p%y + 1
|
||||
|
||||
if ( (cx > 0) .and. (cx <= ubound(ch,1)) .and. &
|
||||
(cy > 0) .and. (cy <= ubound(ch,2)) ) then
|
||||
ch(cx,cy) = v
|
||||
end if
|
||||
end subroutine plot
|
||||
|
||||
subroutine draw_circle_toch(ch, c, radius, v)
|
||||
integer, dimension(:,:), intent(out) :: ch
|
||||
type(point), intent(in) :: c
|
||||
integer, intent(in) :: radius, v
|
||||
|
||||
integer :: f, ddf_x, ddf_y, x, y
|
||||
|
||||
f = 1 - radius
|
||||
ddf_x = 0
|
||||
ddf_y = -2 * radius
|
||||
x = 0
|
||||
y = radius
|
||||
|
||||
call plot(ch, point(c%x, c%y + radius), v)
|
||||
call plot(ch, point(c%x, c%y - radius), v)
|
||||
call plot(ch, point(c%x + radius, c%y), v)
|
||||
call plot(ch, point(c%x - radius, c%y), v)
|
||||
|
||||
do while ( x < y )
|
||||
if ( f >= 0 ) then
|
||||
y = y - 1
|
||||
ddf_y = ddf_y + 2
|
||||
f = f + ddf_y
|
||||
end if
|
||||
x = x + 1
|
||||
ddf_x = ddf_x + 2
|
||||
f = f + ddf_x + 1
|
||||
call plot(ch, point(c%x + x, c%y + y), v)
|
||||
call plot(ch, point(c%x - x, c%y + y), v)
|
||||
call plot(ch, point(c%x + x, c%y - y), v)
|
||||
call plot(ch, point(c%x - x, c%y - y), v)
|
||||
call plot(ch, point(c%x + y, c%y + x), v)
|
||||
call plot(ch, point(c%x - y, c%y + x), v)
|
||||
call plot(ch, point(c%x + y, c%y - x), v)
|
||||
call plot(ch, point(c%x - y, c%y - x), v)
|
||||
end do
|
||||
|
||||
end subroutine draw_circle_toch
|
||||
|
||||
subroutine draw_circle_rgb(img, c, radius, color)
|
||||
type(rgbimage), intent(out) :: img
|
||||
type(point), intent(in) :: c
|
||||
integer, intent(in) :: radius
|
||||
type(rgb), intent(in) :: color
|
||||
|
||||
call draw_circle_toch(img%red, c, radius, color%red)
|
||||
call draw_circle_toch(img%green, c, radius, color%green)
|
||||
call draw_circle_toch(img%blue, c, radius, color%blue)
|
||||
end subroutine draw_circle_rgb
|
||||
|
||||
subroutine draw_circle_sc(img, c, radius, lum)
|
||||
type(scimage), intent(out) :: img
|
||||
type(point), intent(in) :: c
|
||||
integer, intent(in) :: radius, lum
|
||||
|
||||
call draw_circle_toch(img%channel, c, radius, lum)
|
||||
end subroutine draw_circle_sc
|
||||
|
|
@ -0,0 +1,36 @@
|
|||
package raster
|
||||
|
||||
// Circle plots a circle with center x, y and radius r.
|
||||
// Limiting behavior:
|
||||
// r < 0 plots no pixels.
|
||||
// r = 0 plots a single pixel at x, y.
|
||||
// r = 1 plots four pixels in a diamond shape around the center pixel at x, y.
|
||||
func (b *Bitmap) Circle(x, y, r int, p Pixel) {
|
||||
if r < 0 {
|
||||
return
|
||||
}
|
||||
// Bresenham algorithm
|
||||
x1, y1, err := -r, 0, 2-2*r
|
||||
for {
|
||||
b.SetPx(x-x1, y+y1, p)
|
||||
b.SetPx(x-y1, y-x1, p)
|
||||
b.SetPx(x+x1, y-y1, p)
|
||||
b.SetPx(x+y1, y+x1, p)
|
||||
r = err
|
||||
if r > x1 {
|
||||
x1++
|
||||
err += x1*2 + 1
|
||||
}
|
||||
if r <= y1 {
|
||||
y1++
|
||||
err += y1*2 + 1
|
||||
}
|
||||
if x1 >= 0 {
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (b *Bitmap) CircleRgb(x, y, r int, c Rgb) {
|
||||
b.Circle(x, y, r, c.Pixel())
|
||||
}
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
package main
|
||||
|
||||
// Files required to build supporting package raster are found in:
|
||||
// * This task (immediately above)
|
||||
// * Bitmap
|
||||
// * Write a PPM file
|
||||
|
||||
import (
|
||||
"raster"
|
||||
"fmt"
|
||||
)
|
||||
|
||||
func main() {
|
||||
b := raster.NewBitmap(400, 300)
|
||||
b.FillRgb(0xffdf20) // yellow
|
||||
// large circle, demonstrating clipping to image boundaries
|
||||
b.CircleRgb(300, 249, 200, 0xff2020) // red
|
||||
if err := b.WritePpmFile("circle.ppm"); err != nil {
|
||||
fmt.Println(err)
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,28 @@
|
|||
module Circle where
|
||||
|
||||
import Data.List
|
||||
|
||||
type Point = (Int, Int)
|
||||
|
||||
-- Takes the center of the circle and radius, and returns the circle points
|
||||
generateCirclePoints :: Point -> Int -> [Point]
|
||||
generateCirclePoints (x0, y0) radius
|
||||
-- Four initial points, plus the generated points
|
||||
= (x0, y0 + radius) : (x0, y0 - radius) : (x0 + radius, y0) : (x0 - radius, y0) : points
|
||||
where
|
||||
-- Creates the (x, y) octet offsets, then maps them to absolute points in all octets.
|
||||
points = concatMap generatePoints $ unfoldr step initialValues
|
||||
generatePoints (x, y)
|
||||
= [(xop x0 x', yop y0 y') | (x', y') <- [(x, y), (y, x)], xop <- [(+), (-)], yop <- [(+), (-)]]
|
||||
|
||||
-- The initial values for the loop
|
||||
initialValues = (1 - radius, 1, (-2) * radius, 0, radius)
|
||||
|
||||
-- One step of the loop. The loop itself stops at Nothing.
|
||||
step (f, ddf_x, ddf_y, x, y) | x >= y = Nothing
|
||||
| otherwise = Just ((x', y'), (f', ddf_x', ddf_y', x', y'))
|
||||
where
|
||||
(f', ddf_y', y') | f >= 0 = (f + ddf_y' + ddf_x', ddf_y + 2, y - 1)
|
||||
| otherwise = (f + ddf_x, ddf_y, y)
|
||||
ddf_x' = ddf_x + 2
|
||||
x' = x + 1
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
module CircleArrayExample where
|
||||
|
||||
import Circle
|
||||
|
||||
-- A surface is just a 2d array of characters for the purposes of this example
|
||||
type Colour = Char
|
||||
type Surface = Array (Int, Int) Colour
|
||||
|
||||
-- Returns a surface of the given width and height filled with the colour
|
||||
blankSurface :: Int -> Int -> Colour -> Surface
|
||||
blankSurface width height filler = listArray bounds (repeat filler)
|
||||
where
|
||||
bounds = ((0, 0), (width - 1, height - 1))
|
||||
|
||||
-- Generic plotting function. Plots points onto a surface with the given colour.
|
||||
plotPoints :: Surface -> Colour -> [Point] -> Surface
|
||||
plotPoints surface colour points = surface // zip points (repeat colour)
|
||||
|
||||
-- Draws a circle of the given colour on the surface given a center and radius
|
||||
drawCircle :: Surface -> Colour -> Point -> Int -> Surface
|
||||
drawCircle surface colour center radius
|
||||
= plotPoints surface colour (generateCirclePoints center radius)
|
||||
|
||||
-- Converts a surface to a string
|
||||
showSurface image = unlines [[image ! (x, y) | x <- xRange] | y <- yRange]
|
||||
where
|
||||
((xLow, yLow), (xHigh, yHigh)) = bounds image
|
||||
(xRange, yRange) = ([xLow..xHigh], [yLow..yHigh])
|
||||
|
||||
-- Converts a surface to a string and prints it
|
||||
printSurface = putStrLn . showSurface
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
module CircleBitmapExample where
|
||||
|
||||
import Circle
|
||||
import Bitmap
|
||||
import Control.Monad.ST
|
||||
|
||||
drawCircle :: (Color c) => Image s c -> c -> Point -> Int -> ST s (Image s c)
|
||||
drawCircle image colour center radius = do
|
||||
let pixels = map Pixel (generateCirclePoints center radius)
|
||||
forM_ pixels $ \pixel -> setPix image pixel colour
|
||||
return image
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
(de midPtCircle (Img CX CY Rad)
|
||||
(let (F (- 1 Rad) DdFx 0 DdFy (* -2 Rad) X 0 Y Rad)
|
||||
(set (nth Img (+ CY Rad) CX) 1)
|
||||
(set (nth Img (- CY Rad) CX) 1)
|
||||
(set (nth Img CY (+ CX Rad)) 1)
|
||||
(set (nth Img CY (- CX Rad)) 1)
|
||||
(while (> Y X)
|
||||
(when (ge0 F)
|
||||
(dec 'Y)
|
||||
(inc 'F (inc 'DdFy 2)) )
|
||||
(inc 'X)
|
||||
(inc 'F (inc (inc 'DdFx 2)))
|
||||
(set (nth Img (+ CY Y) (+ CX X)) 1)
|
||||
(set (nth Img (+ CY Y) (- CX X)) 1)
|
||||
(set (nth Img (- CY Y) (+ CX X)) 1)
|
||||
(set (nth Img (- CY Y) (- CX X)) 1)
|
||||
(set (nth Img (+ CY X) (+ CX Y)) 1)
|
||||
(set (nth Img (+ CY X) (- CX Y)) 1)
|
||||
(set (nth Img (- CY X) (+ CX Y)) 1)
|
||||
(set (nth Img (- CY X) (- CX Y)) 1) ) ) )
|
||||
|
||||
(let Img (make (do 120 (link (need 120 0)))) # Create image 120 x 120
|
||||
(midPtCircle Img 60 60 50) # Draw circle
|
||||
(out "img.pbm" # Write to bitmap file
|
||||
(prinl "P1")
|
||||
(prinl 120 " " 120)
|
||||
(mapc prinl Img) ) )
|
||||
|
|
@ -0,0 +1,67 @@
|
|||
def circle(self, x0, y0, radius, colour=black):
|
||||
f = 1 - radius
|
||||
ddf_x = 1
|
||||
ddf_y = -2 * radius
|
||||
x = 0
|
||||
y = radius
|
||||
self.set(x0, y0 + radius, colour)
|
||||
self.set(x0, y0 - radius, colour)
|
||||
self.set(x0 + radius, y0, colour)
|
||||
self.set(x0 - radius, y0, colour)
|
||||
|
||||
while x < y:
|
||||
if f >= 0:
|
||||
y -= 1
|
||||
ddf_y += 2
|
||||
f += ddf_y
|
||||
x += 1
|
||||
ddf_x += 2
|
||||
f += ddf_x
|
||||
self.set(x0 + x, y0 + y, colour)
|
||||
self.set(x0 - x, y0 + y, colour)
|
||||
self.set(x0 + x, y0 - y, colour)
|
||||
self.set(x0 - x, y0 - y, colour)
|
||||
self.set(x0 + y, y0 + x, colour)
|
||||
self.set(x0 - y, y0 + x, colour)
|
||||
self.set(x0 + y, y0 - x, colour)
|
||||
self.set(x0 - y, y0 - x, colour)
|
||||
Bitmap.circle = circle
|
||||
|
||||
bitmap = Bitmap(25,25)
|
||||
bitmap.circle(x0=12, y0=12, radius=12)
|
||||
bitmap.chardisplay()
|
||||
|
||||
'''
|
||||
The origin, 0,0; is the lower left, with x increasing to the right,
|
||||
and Y increasing upwards.
|
||||
|
||||
The program above produces the following display :
|
||||
|
||||
+-------------------------+
|
||||
| @@@@@@@ |
|
||||
| @@ @@ |
|
||||
| @@ @@ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
|@ @|
|
||||
|@ @|
|
||||
|@ @|
|
||||
|@ @|
|
||||
|@ @|
|
||||
|@ @|
|
||||
|@ @|
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @ @ |
|
||||
| @@ @@ |
|
||||
| @@ @@ |
|
||||
| @@@@@@@ |
|
||||
+-------------------------+
|
||||
'''
|
||||
|
|
@ -0,0 +1,49 @@
|
|||
/*REXX pgm plots 3 circles using midpoint/Bresenham's circle algorithm. */
|
||||
EoE = 200 /*EOE = End Of Earth, er, plot. */
|
||||
image. = 'fa'x /*fill the array with middle-dots*/
|
||||
pChar = '*'
|
||||
do j=-EoE to +EoE /*draw grid from lowest──>highest*/
|
||||
image.j.0 = '─' /*draw the horizontal axis. */
|
||||
image.0.j = '│' /* " " verical " */
|
||||
end /*j*/
|
||||
image.0.0='┼' /*"draw" the axis origin. */
|
||||
minX=0; maxX=0
|
||||
minY=0; maxY=0
|
||||
call draw_circle 0, 0, 8, '#'
|
||||
call draw_circle 0, 0, 11, '$'
|
||||
call draw_circle 0, 0, 19, '@'
|
||||
border=2
|
||||
minX=minX-border*2; maxX=maxX+border*2
|
||||
minY=minY-border ; maxY=maxY+border
|
||||
do y=maxY by -1 to minY; aRow=
|
||||
do x=minX to maxX
|
||||
aRow=aRow || image.x.y
|
||||
end /*x*/
|
||||
say aRow
|
||||
end /*y*/
|
||||
exit /*stick a fork in it, we're done.*/
|
||||
/*───────────────────────────────────DRAW_CIRCLE subroutine─────────────*/
|
||||
draw_circle: procedure expose image. minX maxX minY maxY
|
||||
parse arg xx, yy, r, point; f=1-r; ddfx=1; ddfy=-2*r; y=r
|
||||
_=yy+r; image.xx._='*'
|
||||
_=xx+r; image._.yy='*'
|
||||
_=yy-r; image.xx._='*'
|
||||
_=xx-r; image._.yy='*'
|
||||
do x=0 while x<y
|
||||
if f>=0 then do; y=y-1; ddfy=ddfy+2; f=f+ddfy; end
|
||||
ddfx=ddfx+2; f=f+ddfx
|
||||
x_=xx+x; y_=yy+y; call plotXY x_, y_, point
|
||||
x_=xx+y; y_=yy+x; call plotXY x_, y_, point
|
||||
x_=xx+y; y_=yy-x; call plotXY x_, y_, point
|
||||
x_=xx+x; y_=yy-y; call plotXY x_, y_, point
|
||||
x_=xx-x; y_=yy-y; call plotXY x_, y_, point
|
||||
x_=xx-y; y_=yy-x; call plotXY x_, y_, point
|
||||
x_=xx-y; y_=yy+x; call plotXY x_, y_, point
|
||||
x_=xx-x; y_=yy+y; call plotXY x_, y_, point
|
||||
end /*x*/
|
||||
return
|
||||
/*──────────────────────────────────PLOTXY subroutine───────────────────*/
|
||||
plotXY: procedure expose image. minX maxX minY maxY; parse arg xx, yy, p
|
||||
image.xx.yy=p; minX=min(minX,xx); maxX=max(maxX,xx)
|
||||
minY=min(minY,yy); maxY=max(maxY,yy)
|
||||
return
|
||||
|
|
@ -0,0 +1,39 @@
|
|||
Pixel = Struct.new(:x, :y)
|
||||
|
||||
class Pixmap
|
||||
def draw_circle(pixel, radius, colour)
|
||||
validate_pixel(pixel.x, pixel.y)
|
||||
|
||||
self[pixel.x, pixel.y + radius] = colour
|
||||
self[pixel.x, pixel.y - radius] = colour
|
||||
self[pixel.x + radius, pixel.y] = colour
|
||||
self[pixel.x - radius, pixel.y] = colour
|
||||
|
||||
f = 1 - radius
|
||||
ddF_x = 1
|
||||
ddF_y = -2 * radius
|
||||
x = 0
|
||||
y = radius
|
||||
while x < y
|
||||
if f >= 0
|
||||
y -= 1
|
||||
ddF_y += 2
|
||||
f += ddF_y
|
||||
end
|
||||
x += 1
|
||||
ddF_x += 2
|
||||
f += ddF_x
|
||||
self[pixel.x + x, pixel.y + y] = colour
|
||||
self[pixel.x + x, pixel.y - y] = colour
|
||||
self[pixel.x - x, pixel.y + y] = colour
|
||||
self[pixel.x - x, pixel.y - y] = colour
|
||||
self[pixel.x + y, pixel.y + x] = colour
|
||||
self[pixel.x + y, pixel.y - x] = colour
|
||||
self[pixel.x - y, pixel.y + x] = colour
|
||||
self[pixel.x - y, pixel.y - x] = colour
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
bitmap = Pixmap.new(30, 30)
|
||||
bitmap.draw_circle(Pixel[14,14], 12, RGBColour::BLACK)
|
||||
|
|
@ -0,0 +1,36 @@
|
|||
object BitmapOps {
|
||||
def midpoint(bm:RgbBitmap, x0:Int, y0:Int, radius:Int, c:Color)={
|
||||
var f=1-radius
|
||||
var ddF_x=1
|
||||
var ddF_y= -2*radius
|
||||
var x=0
|
||||
var y=radius
|
||||
|
||||
bm.setPixel(x0, y0+radius, c)
|
||||
bm.setPixel(x0, y0-radius, c)
|
||||
bm.setPixel(x0+radius, y0, c)
|
||||
bm.setPixel(x0-radius, y0, c)
|
||||
|
||||
while(x < y)
|
||||
{
|
||||
if(f >= 0)
|
||||
{
|
||||
y-=1
|
||||
ddF_y+=2
|
||||
f+=ddF_y
|
||||
}
|
||||
x+=1
|
||||
ddF_x+=2
|
||||
f+=ddF_x
|
||||
|
||||
bm.setPixel(x0+x, y0+y, c)
|
||||
bm.setPixel(x0-x, y0+y, c)
|
||||
bm.setPixel(x0+x, y0-y, c)
|
||||
bm.setPixel(x0-x, y0-y, c)
|
||||
bm.setPixel(x0+y, y0+x, c)
|
||||
bm.setPixel(x0-y, y0+x, c)
|
||||
bm.setPixel(x0+y, y0-x, c)
|
||||
bm.setPixel(x0-y, y0-x, c)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,48 @@
|
|||
package require Tcl 8.5
|
||||
package require Tk
|
||||
|
||||
proc drawCircle {image colour point radius} {
|
||||
lassign $point x0 y0
|
||||
|
||||
setPixel $image $colour [list $x0 [expr {$y0 + $radius}]]
|
||||
setPixel $image $colour [list $x0 [expr {$y0 - $radius}]]
|
||||
setPixel $image $colour [list [expr {$x0 + $radius}] $y0]
|
||||
setPixel $image $colour [list [expr {$x0 - $radius}] $y0]
|
||||
|
||||
set f [expr {1 - $radius}]
|
||||
set ddF_x 1
|
||||
set ddF_y [expr {-2 * $radius}]
|
||||
set x 0
|
||||
set y $radius
|
||||
|
||||
while {$x < $y} {
|
||||
assert {$ddF_x == 2 * $x + 1}
|
||||
assert {$ddF_y == -2 * $y}
|
||||
assert {$f == $x*$x + $y*$y - $radius*$radius + 2*$x - $y + 1}
|
||||
if {$f >= 0} {
|
||||
incr y -1
|
||||
incr ddF_y 2
|
||||
incr f $ddF_y
|
||||
}
|
||||
incr x
|
||||
incr ddF_x 2
|
||||
incr f $ddF_x
|
||||
setPixel $image $colour [list [expr {$x0 + $x}] [expr {$y0 + $y}]]
|
||||
setPixel $image $colour [list [expr {$x0 - $x}] [expr {$y0 + $y}]]
|
||||
setPixel $image $colour [list [expr {$x0 + $x}] [expr {$y0 - $y}]]
|
||||
setPixel $image $colour [list [expr {$x0 - $x}] [expr {$y0 - $y}]]
|
||||
setPixel $image $colour [list [expr {$x0 + $y}] [expr {$y0 + $x}]]
|
||||
setPixel $image $colour [list [expr {$x0 - $y}] [expr {$y0 + $x}]]
|
||||
setPixel $image $colour [list [expr {$x0 + $y}] [expr {$y0 - $x}]]
|
||||
setPixel $image $colour [list [expr {$x0 - $y}] [expr {$y0 - $x}]]
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
# create the image and display it
|
||||
set img [newImage 200 100]
|
||||
label .l -image $img
|
||||
pack .l
|
||||
|
||||
fill $img black
|
||||
drawCircle $img blue {100 50} 49
|
||||
Loading…
Add table
Add a link
Reference in a new issue