Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- local computer = require ("computer")
- ---------------------------------
- local Render = {Color = {}}
- ---------------------------------
- function Render.Color.RGBPack (r, g, b)
- return (r *(256^2)) + (g * 256) + b
- end
- ---------------------------------
- function Render.Color.RGBExtract (color)
- color = color % 0x1000000
- local r = math.floor(color / 0x10000)
- local g = math.floor((color - r * 0x10000) / 0x100)
- local b = color - r * 0x10000 - g * 0x100
- return r, g, b
- end
- ---------------------------------
- function Render.Color.Interpolate (a, b, t)
- local ar, ag, ab = Render.Color.RGBExtract (a)
- local br, bg, bb = Render.Color.RGBExtract (b)
- return Render.Color.RGBPack (math.floor (ar + (br - ar) * t),
- math.floor (ag + (bg - ag) * t),
- math.floor (ab + (bb - ab) * t))
- end
- ---------------------------------
- function Render.InterpolatePoint (a, b, t)
- local point = {}
- point.x = a.x + t * (b.x - a.x)
- point.y = a.y + t * (b.y - a.y)
- point.z = a.z + t * (b.z - a.z)
- if t > 1 or t < 0 then computer.beep (1000, 0.01) end
- point.color = Render.Color.Interpolate (a.color, b.color, t)
- return point
- end
- ---------------------------------
- function Render.SortPointsByY (a, b, c)
- if (c.y < a.y) then local tc = c; c = a; a = tc end
- if (c.y < b.y) then local tc = c; b = c; c = tc end
- if (b.y < a.y) then local ta = a; a = b; b = ta end
- return a, b, c
- end
- ---------------------------------
- function Render.Triangle (a, b, c, setpixel_func, renderscale)
- local renderscale = renderscale or 1
- a, b, c = Render.SortPointsByY (a, b, c)
- if a.y == c.y then
- if a.x == c.x then
- setpixel_func (a.x, a.y, a.z, a.color)
- return
- end
- if a.x > c.x then local tx = a.x; a.x = c.x; c.x = tx end
- local dt = 1 / (c.x - a.x)
- local t = 0;
- for x = a.x, c.x do
- if t > 1 then t = 1 end
- local d = Render.InterpolatePoint (a, c, t)
- setpixel_func (d.x, d.y, d.z, d.color)
- t = t + dt
- end
- return
- elseif a.y == b.y then
- if a.y > c.y then ta = a; a = c; c = ta end
- local dt0 = 1 / (c.y - a.y)
- local t0 = dt0
- for y = a.y, c.y do
- if t0 > 1 then t0 = 1 end
- local e = Render.InterpolatePoint (a, c, t0)
- local f = Render.InterpolatePoint (b, c, t0)
- e.y = y
- f.y = y
- if e.x == f.x then
- setpixel_func (e.x, e.y, e.z, e.color)
- else
- if f.x > e.x then local tf = f; f = e; e = tf end
- local dt1 = 1 / (e.x - f.x)
- local t1 = 0;
- for x = f.x, e.x do
- if t1 > 1 then t1 = 1 end
- g = Render.InterpolatePoint (f, e, t1)
- g.x = x;
- setpixel_func (g.x, g.y, g.z, g.color)
- t1 = t1 + dt1
- end
- end
- t0 = t0 + dt0
- end
- return
- elseif c.y == b.y then
- local dt0 = 1 / (c.y - a.y)
- local t0 = 0;
- for y = a.y, c.y do
- if t0 > 1 then t0 = 1 end
- e = Render.InterpolatePoint (a, c, t0)
- f = Render.InterpolatePoint (a, b, t0)
- e.y = y
- f.y = y
- if t0 > 1 then t0 = 1 end
- if e.x == f.x then
- setpixel_func (e.x, e.y, e.z, e.color)
- else
- if f.x > e.x then tf = f; f = e; e = tf end
- local dt1 = 1 / (e.x - f.x)
- local t1 = 0
- local ex = math.floor (e.x)
- if a.y < c.y then ex = math.ceil (e.x) end
- for x = f.x, ex do
- if t1 > 1 then t1 = 1 end
- local g = Render.InterpolatePoint (f, e, t1)
- g.x = x
- setpixel_func (g.x, g.y, g.z, g.color)
- t1 = t1 + dt1
- end
- end
- t0 = t0 + dt0
- end
- return
- else
- local d = Render.InterpolatePoint (a, c, (b.y - a.y) / (c.y - a.y))
- if d.y == a.y then return end
- local dt0 = 1 / (d.y - a.y) / renderscale
- local t0 = 0;
- for y = a.y, d.y, 1 / renderscale do
- if t0 > 1 then t0 = 1 end
- local e = Render.InterpolatePoint (a, d, t0)
- local f = Render.InterpolatePoint (a, b, t0)
- e.y = y
- f.y = y
- if t0 > 1 then t0 = 1 end
- if e.x == f.x then
- setpixel_func (e.x, e.y, e.y, e.color);
- else
- if f.x > e.x then local tf = f; f = e; e = tf end
- local dt1 = 1 / (e.x - f.x) / renderscale;
- local t1 = 0;
- for x = f.x, e.x, 1 / renderscale do
- if t1 > 1 then t1 = 1 end
- local g = Render.InterpolatePoint (f, e, t1)
- setpixel_func (x, g.y, g.z, g.color)
- t1 = t1 + dt1
- end
- end
- t0 = t0 + dt0
- end
- if d.y == c.y then return end
- dt0 = 1 / (c.y - d.y) / renderscale
- t0 = dt0;
- for y = d.y, c.y, 1 / renderscale do
- if t0 > 1 then t0 = 1 end
- local e = Render.InterpolatePoint (d, c, t0)
- local f = Render.InterpolatePoint (b, c, t0)
- e.y = y
- f.y = y
- if e.x == f.x then
- setpixel_func (e.x, e.y, e.z, e.color);
- else
- if f.x > e.x then local tf = f; f = e; e = tf end
- local dt1 = 1 / (e.x - f.x) / renderscale;
- local t1 = 0;
- local ex = e.x
- if b.x < c.x then e.x = e.x + 2 else e.x = e.x - 2 end
- for x = f.x, ex, 1 / renderscale do
- if t1 > 1 then t1 = 1 end
- local g = Render.InterpolatePoint (f, e, t1)
- setpixel_func (x, g.y, g.z, g.color)
- t1 = t1 + dt1
- end
- end
- t0 = t0 + dt0
- end
- end
- end
- ---------------------------------
- return Render
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement