Skip to content

Instantly share code, notes, and snippets.

@Snektron
Last active October 18, 2020 01:12
Show Gist options
  • Save Snektron/691667659df8cf002f229dce1edbed12 to your computer and use it in GitHub Desktop.
Save Snektron/691667659df8cf002f229dce1edbed12 to your computer and use it in GitHub Desktop.
const std = @import("std");
const Vec3 = struct {
x: f32,
y: f32,
z: f32,
const up = Vec3{.x = 0, .y = 1, .z = 0};
fn add(a: Vec3, b: Vec3) Vec3 {
return .{.x = a.x + b.x, .y = a.y + b.y, .z = a.z + b.z};
}
fn sub(a: Vec3, b: Vec3) Vec3 {
return .{.x = a.x - b.x, .y = a.y - b.y, .z = a.z - b.z};
}
fn mul(a: Vec3, b: Vec3) Vec3 {
return .{.x = a.x * b.x, .y = a.y * b.y, .z = a.z * b.z};
}
fn scale(self: Vec3, scalar: f32) Vec3 {
return .{.x = self.x * scalar, .y = self.y * scalar, .z = self.z * scalar};
}
fn magnitudeSq(self: Vec3) f32 {
return self.x * self.x + self.y * self.y + self.z * self.z;
}
fn magnitude(self: Vec3) f32 {
return @sqrt(self.magnitudeSq());
}
fn normalize(self: Vec3) Vec3 {
const m = self.magnitude();
return self.scale(1 / m);
}
fn dot(a: Vec3, b: Vec3) f32 {
return a.x * b.x + a.y * b.y + a.z * b.z;
}
fn cross(a: Vec3, b: Vec3) Vec3 {
return .{
.x = a.y * b.z - a.z * b.y,
.y = a.z * b.x - a.x * b.z,
.z = a.x * b.y - a.y * b.x,
};
}
};
const width = 80;
const height = 40;
const steps = 10;
const epsilon = 0.05;
const light = (Vec3{.x = 2, .y = 1, .z = 1}).normalize();
fn scene(p: Vec3) f32 {
// return p.magnitude() - 1;
const tx = 1.0;
const ty = 0.8;
const qx = @sqrt(p.z * p.z + p.y * p.y) - tx;
const qy = p.x;
return @sqrt(qx * qx + qy * qy) - ty;
}
fn normal(p: Vec3) Vec3 {
const d0 = scene(p);
const nx = scene(p.add(Vec3{.x = epsilon, .y = 0, .z = 0})) - d0;
const ny = scene(p.add(Vec3{.x = 0, .y = epsilon, .z = 0})) - d0;
const nz = scene(p.add(Vec3{.x = 0, .y = 0, .z = epsilon})) - d0;
return (Vec3{.x = nx, .y = ny, .z = nz}).normalize();
}
fn raymarch(ro: Vec3, rd: Vec3) f32 {
var i: usize = 0;
var t: f32 = 0.0;
while (i < steps) : (i += 1) {
const p = rd.scale(t).add(ro);
const h = scene(p);
t += h;
if (h < epsilon) {
// hit
return t;
} else if (t > 10) {
// max distance, miss
return -1;
}
}
// miss
return -1;
}
fn tan(x: anytype) @TypeOf(x) {
return @sin(x) / @cos(x);
}
fn ray(x: isize, y: isize, fwd: Vec3) Vec3 {
const u = (@intToFloat(f32, x) + 0.5) / width;
const v = (@intToFloat(f32, y) + 0.5) / height;
var f = @sqrt(u * u + v * v);
f = 1 / tan(f * 1.17); // fov of 67 degrees
const right = Vec3.cross(fwd, Vec3.up).normalize();
const up = Vec3.cross(fwd, right).normalize();
return fwd.scale(f).add(up.scale(v)).add(right.scale(u)).normalize();
}
fn trace(x: isize, y: isize) f32 {
const u = @intToFloat(f32, x) / width;
const v = @intToFloat(f32, y) / height;
const ro = Vec3{.x = 7, .y = 0, .z = 0};
const rd = ray(x, y, Vec3{.x = -1, .y = 0, .z = 0});
const t = raymarch(ro, rd);
if (t < 0) {
return 0;
}
const p = rd.scale(t).add(ro);
const n = normal(p);
return std.math.max(0.02, n.dot(light));
}
fn intensityToChar(v: f32) u8 {
const ramp = "$@B%8&WM#*oahkbdpqwmZO0QLCJUYXzcvunxrjft/\\|()1{}[]?-_+~<>i!lI;:,\"^'. ";
const index = @floatToInt(usize, v * @intToFloat(f32, ramp.len));
return ramp[ramp.len - 1 - std.math.clamp(index, 0, ramp.len - 1)];
}
fn rt() void {
@setEvalBranchQuota(1000000);
var out: []const u8 = "\n";
var y: isize = -height / 2;
while (y < height / 2) : (y += 1) {
var x: isize = -width / 2;
while (x < width / 2) : (x += 1) {
const v = trace(x, y);
out = out ++ [_]u8{ intensityToChar(v) };
}
@compileLog(y);
out = out ++ "\n";
}
@compileError(out);
}
pub fn main() void {
comptime rt();
}
./ctrt.zig:152:9: error: found compile log statement
@compileLog(y);
^
./ctrt.zig:129:15: note: referenced here
const n = normal(p);
^
./ctrt.zig:131:32: note: referenced here
return std.math.max(0.02, n.dot(light));
^
./ctrt.zig:131:37: note: referenced here
return std.math.max(0.02, n.dot(light));
^
./ctrt.zig:156:5: error:
ba*#MMM###**oahbpm0U
#W8%%%%%%%888&&&WWMM#**ohbpwQU
M8B@@@@BB%%88&&WWMMMMMMM####**oakdqZJv
M%@$$$@B%8&WWM#**oooaaaaaooooo****ooahbdw0Ux
8@$$$@B%8WM#oahkbddppppppppddbkkhhaaoooaahkdw0Jn
q8@$$$@%8WM*akbpqmZO00QQQQQQ00OZmwqpdbkhhaaaaahbpw0Ur>
&@$$$@%&M*akdqmOQCJYXzcccccczzXYJCL0OmwqdbkhhaaahkdqZLz/
*B$$$@%&M*hbqm0LUXcuxrftt////ttfrxuvzYJL0Zmqpbkhhaahkbpm0Yx-
W@$$@B8M*hbqZQJXvnjt|)1}[]]??][}{)(\frncXUL0Zwqdbkhaahhbdw0Un{
W@$@B%&#akqZQJzurt|1[-+<>!lllllli<+?[1(/jncYJQOmqdbkhaaahkdw0Un{
WB@@B8W*hdwOCXvr/(}?+>l:".........^,Ii+?{|txvXJLOmqdbhhaaahkpmQYr[
#%@@B8W*hdm0Jznf|{?~i;"..............."I>_[)/xvXJQZwpbkhaaaahbpZLzt_
k8BBB8W*hdw0Jznf(}->I"...................^l_[(txcULOmqdkhaoooakdqOJn(;
#%B%8W#abqOCXuf|}->;^........ ..!_1\rvYC0mqdkaoooooakpmLzf-
bW%%8&MokpmQUcr/1?<l^....... .i[(jvXCOmpbhao***oahdw0Yx1"
aW88&W#abqOCXuj|}_>;...... -(jcYLZwdkao*###*ohbqOJu(i
aW88&M*hdw0CXnf(}_i,...... _(xXC0mpbho*##M##*akpZJv|<
oM&&WMohdw0CXuj|{->:..... tvU0mpbho*#MWWM#*akpZJv\+
a#WWW#ohdwOLYvr/)]+l".... nUQmpka*#MWW&WWM*akqOJu(~
b*MWM#ohbqZQJznf\1?<l,.... rUOqbho#MW&&8&&WM*abq0Yx1l
qa#MM#*akpwOLUcnf\1[+i;'.. Lwdho#M&&8%%%8&WM*hdmLzj["
Lbo###*ohbpm0LUzuj/({?+>I,.. Umbh*#W&8%%BBB%8&W#okqOJu|+.
mko***oakdqmOLJXvnjt\1}]-~>I" Jmba#M&8%BB@@@@B%8&M*hdmLzf[,
Yqko**ooakbpwZ0LUXcuxrt/|((1{{}}1{)\fvYLwdh#M&8%B@@$$$@@B%8W#abwQYx1>.
CqkaoooahkbdqmZ0LCUYzcvunnxnnunvcXJLOwbh*MW8%B@$$$$$$@B%8W#abw0Yn|+.
CwbhaooaahkbpqwmO0QLCCJJJUUJCLQ0Zwpbho#W&%B@@$$$$$$@B%&W#abw0Yn|+.
UZpkhaaaahhkbdpqqwmmZZZZZZmwwqdbkao#M&8%B@@$$$$$@@B8&M*hdmQXx(+.
cQwdkhhaaahhhkbbbdddpppddbbkhao*#MW&8%B@@@$$@@B%8&M*abqOJcj{>.
tU0wpbkhhaaaahhhhhhhhhhaaoo*##MW&88%%BBBBBB%%8&M*akpZLXn\?;.
nJ0mpdbkhhaaaaaaaoooo**##MMWW&&88%%%%%88&WM#ohbqZLYut}i.
~xYLZwpdbkhhaaaooo***###MMWWW&&&&&&WWM#*ohbpwOCXn/}>..
tcUQOmqpdbkkhhaaoo****########**oahkdqmOLYvj|]i.
{juXCQOZwqpddbbkkhhhhhhhhhkbbdpwmOQJXuj\[~:.
](juzYJLQ0OZZmmwwwwwmmZO0QLJYzur/1?>^.
_}|tjxuczzXXXXXXzcvunrf\)[_i^.
"i~_][}}}}[[?-+>I"..
@compileError(out);
^
./ctrt.zig:160:16: note: called from here
comptime rt();
^
./ctrt.zig:159:20: note: called from here
pub fn main() void {
^
./ctrt.zig:160:16: note: referenced here
comptime rt();
^
./ctrt.zig:149:49: error: unable to evaluate constant expression
out = out ++ [_]u8{ intensityToChar(v) };
^
./ctrt.zig:149:48: note: referenced here
out = out ++ [_]u8{ intensityToChar(v) };
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment