kolibrios/programs/games/codemaster/include/draw.inc
codemaster 13694b9ade Added 3 games for the New Year competition: Binary Master, Hang Programmer, Kolibri Puzzle
(Author: codemaster; initially sources are uploaded to SVN "as is" without modification)
### Redo r.5303 with correct letter case for auto-build machine ###

git-svn-id: svn://kolibrios.org@5305 a494cfbc-eb01-0410-851d-a64ba20cac60
2014-12-30 23:59:59 +00:00

385 lines
7.8 KiB
PHP

; $$$$$$$$$$$$$$$$$$$ ABAKIS $$$$$$$$$$$$$$$$$$$$$
; *************** STAR^2 SOFTWARE ****************
; ?????????????????? DRAW.INC ????????????????????
; fast portable graphics
include 'color.inc'
include 'box.inc'
;;;;;;;;;;;;;;;;;;;;; SCREEN ;;;;;;;;;;;;;;;;;;;;;
align
void vga.p
integer screen.x, screen.y,\
screen.w, screen.h, screen.n,\
screen.bpp, screen.size,\
screen.pw, screen.pitch
void palette.p
BOX g.box
function set.screen, w, h, bpp
alias n=r0, pw=r1
. screen.w=w, screen.h=h ; size
. n=w, n*h, screen.n=n ; # pixels
. pw=bpp, pw/8 ; pixel width
. screen.pw=pw, n*pw ; screen size
. screen.size=n ; in bytes
. n=w, n*pw ; screen pitch
. screen.pitch=n ; w in bytes
. screen.bpp=bpp ; bits per pixel
endf
;;;;;;;;;;;;;;;;;;;; DRAWING ;;;;;;;;;;;;;;;;;;;;;
; erase screen with color
function clear.screen, c
alias p=r0, n=r1, z=r2
. p=vga.p, n=screen.n, z=c
loop n, (u32) *p++=z, endl
endf
; calculate x/y offset: (y*screen.w+x)*4
macro get.xy x, y
{ . r0=y, r0*screen.w, r0+x, r0*4 }
; address &vga[(y*screen.w+x)*4]
function vga.xy, x, y
get.xy x, y
. r0+vga.p
endf
; draw pixel
function draw.pixel, x, y, c
alias p=r0, z=r1
try clip.pixel x, y
vga.xy x, y
. z=c, (u32) *p=z
endf 1
; draw horizontal line
function draw.line.h, x, y, n, c
alias p=r0, z=r1, w=r2
. p=&x, z=&y, w=&n
try clip.line 0, p, z, w
vga.xy x, y
. z=c
loop n, (u32) *p++=z, endl
endf 1
; draw vertical line
function draw.line.v, x, y, n, c
locals swb
alias p=r0, z=r1, h=r2
. p=&x, z=&y, h=&n
try clip.line 1, p, z, h
vga.xy x, y
. z=c, swb=screen.pitch
loop n, (u32) *p=z, p+swb, endl
endf 1
; draw solid rectangle
function draw.box, x, y, w, h, c
locals i
try visible x, y, w, h
. i=y, i--
loop h, i++
draw.line.h x, i, w, c
endl
endf 1
; draw rectangle outline
function draw.outline, x, y, w, h, c
try visible x, y, w, h
draw.line.h x, y, w, c ; top
. r0=y, r0+h, r0-- ; bottom
draw.line.h x, r0, w, c
. r0=y, r0++, r1=h, r1-2 ; left
draw.line.v x, r0, r1, c
. r0=x, r0+w, r0--
. r2=y, r2++, r1=h, r1-2 ; right
draw.line.v r0, r2, r1, c
endf 1
macro draw.box.s b, c
{ draw.box b#.x, b#.y, b#.w, b#.h, c }
macro draw.box.o b, c
{ draw.outline b#.x, b#.y, b#.w, b#.h, c }
macro draw.box a, b, c, d, e {
IF ~e eq
draw.box a, b, c, d, e
ELSE IF ~d eq
'Unsupported'
ELSE IF ~c eq
draw.box.s a, b
draw.box.o a, c
ELSE IF ~b eq
draw.box.s a, b
END IF
}
; draw scanline
function draw.scanline, pixels, x, y, w
locals i
alias p=r0, s=r1
. r0=&i, r1=&x, r2=&y, r3=&w
try clip.scanline r0, r1, r2, r3
vga.xy x, y
. s=pixels, s+i
loop w, (u32) *p++=*s++, endl
endf 1
; draw scanline with transparent key
function draw.scanline.t, pixels, x, y, w, key
locals i
alias p=r0, s=r1, c=r2
. r0=&i, r1=&x, r2=&y, r3=&w
try clip.scanline r0, r1, r2, r3
vga.xy x, y
. s=pixels, s+i
loop w, (u32) c=*s++
if c<>key, (u32) *p=c, end, p+4
endl
endf 1
; draw scanline with inverted x
function draw.scanline.ix, pixels, x, y, w
locals i
alias p=r0, s=r1
. r0=x, r0+w
vga.xy r0, y
. p-4, s=pixels
loop w, (u32) *p--=*s++, endl
endf 1
; draw variant scanline. pixels are
; grayscale, alpha intensity of co=color.
; for brushes and special effects
function draw.scanline.v, pixels, x, y, w, co
locals a, i
alias p=r0, s=r1, c=r2, c2=r3
. r0=&i, r1=&x, r2=&y, r3=&w
try clip.scanline r0, r1, r2, r3
vga.xy x, y
. s=pixels, s+i
loop w, (u32) c=*s++
. a=c, a&0FFh
if a=0, go .next, end
if a=0FFh, c=co, go .draw, end
. (u32) c2=*p
push p s
get c=mix co, c2, a
pop s p
.draw: . (u32) *p=c
.next: . p+4
endl
endf 1
; draw bitmap
function draw.bitmap, pixels, x, y, w, h
locals i, p
try visible x, y, w, h
. i=y, p=pixels
loop h
draw.scanline p, x, i, w
. r0=w, r0*4, p+r0, i++
endl
endf 1
; draw bitmap with transparency by
; upper left pixel color (X=0, Y=0)
function draw.bitmap.t, pixels, x, y, w, h
locals i, p, key
try visible x, y, w, h
. i=y, r0=pixels, p=r0
. (u32) r0=*r0, key=r0
loop h
draw.scanline.t p, x, i, w, key
. r0=w, r0*4, p+r0, i++
endl
endf 1
; draw bitmap with inverted x
function draw.bitmap.ix, pixels, x, y, w, h
locals i, p
try visible x, y, w, h
. p=pixels
loop h
draw.scanline.ix p, x, y, w
. r0=w, r0*4, p+r0, y++
endl
endf 1
; draw bitmap with inverted y
function draw.bitmap.iy, pixels, x, y, w, h
locals i, p
try visible x, y, w, h
. r0=h, r0--, y+r0, p=pixels
loop h
draw.scanline p, x, y, w
. r0=w, r0*4, p+r0, y--
endl
endf 1
; draw bitmap with both inverted
function draw.bitmap.ixy, pixels, x, y, w, h
locals i, p, n
try visible x, y, w, h
. p=pixels
loop h
draw.scanline.ix p, x, y, w
. r0=w, r0*4, p+r0, y--
endl
endf 1
; draw variant bitmap
function draw.bitmap.v, pixels, x, y, w, h, c
locals i, p
try visible x, y, w, h
. i=y, r0=pixels, p=r0
loop h
draw.scanline.v p, x, i, w, c
. r0=w, r0*4, p+r0, i++
endl
endf 1
; draw gradual vertical fade from
; color a to b. o/rient:
; 'h'=horizontal, 'v'=vertical
function draw.fade, bo, c1, c2
locals x, y, w, h, i, n, c,\
r, g, b, red, green, blue,\
nr, ng, nb, first, last
. r0=bo,\
x=[?box.x+r0], y=[?box.y+r0],\
w=[?box.w+r0], h=[?box.h+r0]
. r0=y, first=r0, r1=h
. n=r1, r0+r1, last=r0
. r0=&r, r1=&g, r2=&b
get.rgb c1, r0, r1, r2
. r0=&red, r1=&green, r2=&blue
get.rgb c2, r0, r1, r2
. r<<8, g<<8, b<<8, r1=n
if r1=0, r1++, end
. r0=red, r0<<8, r0-r, r0/r1, nr=r0
. r0=green, r0<<8, r0-g, r0/r1, ng=r0
. r0=blue, r0<<8, r0-b, r0/r1, nb=r0
. i=first
forever
. r0=r, r0>>8, r1=g, r1>>8, r2=b, r2>>8
get c=rgb r0, r1, r2
draw.line.h x, i, w, c
. r0=nr, r+r0, r1=ng, g+r1, r2=nb, b+r2
. i++, r0=last
if i>r0, go .out, end
endfv
.out:
endf
; draw with vertical center fade:
; a to b then b to a
function draw.shade, bo, a, b
memory.copy g.box, bo, 16
. g.box.h>>>1
draw.fade g.box, a, b
. r0=g.box.h, g.box.y+r0
draw.fade g.box, b, a
endf
;;;;;;;;;;;;;;;;; PALETTE PIXELS ;;;;;;;;;;;;;;;;;
; 8BPP versions with pa/lette. no clipping
function draw.scanline.8, pixels, x, y, w
alias p=r0, s=r1, c=r2, q=r3
vga.xy x, y
. s=pixels
loop w, q=*s++, q*4, q+palette.p
. (u32) c=*q, (u32) *p++=c
endl
endf 1
function draw.bitmap.8, pixels, x, y, w, h
locals i, p
try visible x, y, w, h
. i=y, i--, p=pixels
loop h, i++
draw.scanline.8 p, x, i, w
. r0=w, p+r0
endl
endf 1
;;;;;;;;;;;;;;;;;;;;; SPECIAL ;;;;;;;;;;;;;;;;;;;;
; special variant 8BPP with alpha bias for
; fonts and sketching effects (example:
; chalkboard)
A.LIGHTEST=128
A.LIGHTER=96
A.LIGHT=64
A.DARK=-32
A.DARKER=-64
A.DARKEST=-96
align
integer alpha.bias=0 ; A.DARKEST
function draw.scanline.v.8, pixels, x, y, w, co
locals a, i
alias p=r0, s=r1, c=r2, c2=r3, q=r3
vga.xy x, y
. s=pixels
loop w, q=*s++, q*4, q+palette.p
. (u32) c=*q, a=c, a&0FFh
if a=0, go .next, end
. (u32) c2=*p
push p s
. r0=a
if alpha.bias, r0+alpha.bias
if r0<0, r0=0
else.if r0>255, r0=255, end
end
get c=mix co, c2, r0
pop s p
.draw: . (u32) *p=c
.next: . p+4
endl
endf 1
function draw.bitmap.v.8, pixels, x, y, w, h, c
locals i, p
try visible x, y, w, h
. i=y, i--, p=pixels
loop h, i++
draw.scanline.v.8 p, x, i, w, c
. r0=w, p+r0
endl
endf 1