Death Star: Difference between revisions

Updated D entry
(Updated D entry)
Line 153:
 
@property V3 normalize() pure nothrow const {
immutable double len = dotProduct(v, v).sqrt();
return [v[0] / len, v[1] /return V3(len, v[2] / len)].V3;
return V3([v[0] / len, v[1] / len, v[2] / len]);
}
 
Line 169 ⟶ 168:
void drawSphere(in double k, in double ambient, in V3 light) nothrow {
/** Check if a ray (x,y, -inf).(x, y, inf) hits a sphere; if so,
return the intersecting z values. z1 is closer to the eye .*/
static bool hitSphere(in ref Sphere sph,
in double x0, in double y0,
Line 179 ⟶ 178:
if (zsq < 0)
return false;
immutable double szsq = sqrt(zsq).sqrt;
z1 = sph.cz - szsq;
z2 = sph.cz + szsq;
Line 185 ⟶ 184:
}
 
enum stringimmutable shades = ".:!*oe&#%@";
// positivePositive and negative spheres.
immutable pos = Sphere(20, 20, 0, 20);
immutable neg = Sphere(1, 1, -6, 20);
 
foreach (immutable int i; cast(int)floor(pos.cy - pos.r) ..
cast(int)ceil(pos.cy + pos.r) + 1) {
immutable double y = i + 0.5;
jloopJLOOP:
foreach (int j; cast(int)floor(pos.cx - 2 * pos.r) ..
cast(int)ceil(pos.cx + 2 * pos.r) + 1) {
Line 199 ⟶ 198:
 
enum Hit { background, posSphere, negSphere }
 
Hit hitResult;
double zb1, zs2;
immutable Hit hitResult = {
double zb2, zs1;
 
if (!hitSphere(pos, x, y, zb1, zb2)) {
// Ray lands in blank space, draw bg.
hitResult =return Hit.background;
} else if (!hitSphere(neg, x, y, zs1, zs2)) {
// Ray hits pos sphere but not neg one,
// draw pos sphere surface.
hitResult =return Hit.posSphere;
} else if (zs1 > zb1) {
// ray hits both, but pos front surface is closer.
hitResult =return Hit.posSphere;
} else if (zs2 > zb2) {
// pos sphere surface is inside neg sphere,
// show bg.
hitResult =return Hit.background;
} else if (zs2 > zb1) {
// Back surface on neg sphere is inside pos
// sphere, the only place where neg sphere
// surface will be shown.
hitResult =return Hit.negSphere;
} else {
hitResult =return Hit.posSphere;
}
}();
 
V3 vec_;
final switch (hitResult) {
case Hit.background:
putchar(' ').putchar;
continue jloopJLOOP;
case Hit.posSphere:
vec_ = V3([x - pos.cx, y - pos.cy, zb1 - pos.cz]).V3;
break;
case Hit.negSphere:
vec_ = V3([neg.cx - x, neg.cy - y, neg.cz - zs2]).V3;
break;
}
immutable V3 nvec = vec_.normalize;
 
immutable double b = light.dot(nvec) ^^ k + ambient;
intimmutable intensity = cast(int)((1 - b) * shades.length);
intensityimmutable normInt = min(shades.length, max(0, intensity));
putchar(shades[intensitynormInt]).putchar;
}
 
putchar('\n').putchar;
}
}
Line 253:
 
void main() {
enumimmutable light = V3([-50, 30, 50]).V3.normalize;
drawSphere(2, 0.5, light);
}</lang>
 
The output is the same of the C version.