Sample

Schnappinger/aoi/artofillusion.raytracer.RTTriangleLowMemory

Human rating uses the original dataset scale.

Human3.06
Lines436

Scores

MethodScoreScaleDataset rank
(0–100)
Posnett00–1; higher is more readable
10.7Δ 21.0
Scalabrino0.6680–1; higher is more readable
31.2Δ 0.5
Dorn0.0060–1; higher is more readable
17.5Δ 14.2
Mi0.7890–1; higher is more readable
94.7Δ 63.0
LLOC265Logical lines; fewer is more readable
8.6Δ 23.1
DeepSeek V4 Pro11.670–20; mean of three runs
13.9Δ 17.8
GPT-6.1 Sol140–20; mean of three runs
16.2Δ 15.5
BTTF0.1930–1; higher is more readable
10.2Δ 21.5
Human3.061–4; original rating
31.7

Views

Source code

/* Copyright (C) 1999-2013 by Peter Eastman This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. */ package artofillusion.raytracer; import artofillusion.*; import artofillusion.material.*; import artofillusion.math.*; import artofillusion.texture.*; /** * RTTriangleLowMemory is identical to {@link RTTriangle}, except that it precalculates * less information. This means that it is slightly slower, but also uses less memory. */ public class RTTriangleLowMemory extends RTObject { RenderingTriangle tri; short dropAxis, flags; Mat4 toLocal, fromLocal; public static final double TOL = 1e-12; private static final short BUMP_MAPPED = 1; private static final short INTERP_NORMALS = 2; public RTTriangleLowMemory(RenderingMesh mesh, int which, Mat4 fromLocal, Mat4 toLocal) { tri = mesh.triangle[which]; Vec3 trueNorm = mesh.faceNorm[which]; this.fromLocal = fromLocal; this.toLocal = toLocal; if (tri.n1 != tri.n2 || tri.n1 != tri.n3) { flags |= INTERP_NORMALS; Vec3 norm1 = mesh.norm[tri.n1]; Vec3 norm2 = mesh.norm[tri.n2]; Vec3 norm3 = mesh.norm[tri.n3]; // Make sure trueNorm points in the same direction as the vertex normals. int i = 0; if (trueNorm.dot(norm1) < 0.0) i++; if (trueNorm.dot(norm2) < 0.0) i++; if (trueNorm.dot(norm3) < 0.0) i++; if (i > 1) trueNorm.scale(-1.0); } if (Math.abs(trueNorm.y) > Math.abs(trueNorm.x)) { if (Math.abs(trueNorm.z) > Math.abs(trueNorm.y)) dropAxis = 2; else dropAxis = 1; } else { if (Math.abs(trueNorm.z) > Math.abs(trueNorm.x)) dropAxis = 2; else dropAxis = 0; } if (tri.theMesh.mapping.getTexture().hasComponent(Texture.BUMP_COMPONENT)) flags |= BUMP_MAPPED; } /** Get the TextureMapping for this object. */ public final TextureMapping getTextureMapping() { return tri.getTextureMapping(); } /** Get the MaterialMapping for this object. */ public final MaterialMapping getMaterialMapping() { return tri.theMesh.matMapping; } /** Determine whether the given ray intersects this triangle. */ public SurfaceIntersection checkIntersection(Ray r) { Vec3 orig = r.getOrigin(), dir = r.getDirection(); RenderingMesh mesh = tri.theMesh; Vec3 trueNorm = mesh.faceNorm[tri.index]; double vd = trueNorm.dot(dir); if (vd == 0.0) return SurfaceIntersection.NO_INTERSECTION; // The ray is parallel to the plane. Vec3 vert1 = mesh.vert[tri.v1]; double v0 = trueNorm.x*(vert1.x-orig.x)+trueNorm.y*(vert1.y-orig.y)+trueNorm.z*(vert1.z-orig.z); double t = v0/vd; if (t < TOL) return SurfaceIntersection.NO_INTERSECTION; // Ray points away from plane of triangle. // Determine whether the intersection point is inside the triangle. double rix = orig.x+dir.x*t; double riy = orig.y+dir.y*t; double riz = orig.z+dir.z*t; double edge2d1x, edge2d1y, edge2d2x, edge2d2y; Vec3 vert2 = mesh.vert[tri.v2]; Vec3 vert3 = mesh.vert[tri.v3]; double vx, vy; switch (dropAxis) { case 0: vx = riy - vert1.y; vy = riz - vert1.z; edge2d1x = vert1.y-vert2.y; edge2d1y = vert1.z-vert2.z; edge2d2x = vert1.y-vert3.y; edge2d2y = vert1.z-vert3.z; break; case 1: vx = rix - vert1.x; vy = riz - vert1.z; edge2d1x = vert1.x-vert2.x; edge2d1y = vert1.z-vert2.z; edge2d2x = vert1.x-vert3.x; edge2d2y = vert1.z-vert3.z; break; default: vx = rix - vert1.x; vy = riy - vert1.y; edge2d1x = vert1.x-vert2.x; edge2d1y = vert1.y-vert2.y; edge2d2x = vert1.x-vert3.x; edge2d2y = vert1.y-vert3.y; } double denom = 1.0/(edge2d1x*edge2d2y-edge2d1y*edge2d2x); edge2d2x *= denom; edge2d2y *= denom; double v = edge2d2x*vy - edge2d2y*vx; if (v < -TOL || v > 1.0+TOL) return SurfaceIntersection.NO_INTERSECTION; edge2d1x *= denom; edge2d1y *= denom; double w = vx*edge2d1y - vy*edge2d1x; if (w < -TOL || w > 1.0+TOL) return SurfaceIntersection.NO_INTERSECTION; double u = 1.0-v-w; if (u < -TOL || u > 1.0+TOL) return SurfaceIntersection.NO_INTERSECTION; TriangleIntersection intersection = (r.rt == null ? new TriangleIntersection() : (TriangleIntersection) r.rt.rtTriPool.getObject()); intersection.init(this, t, u, v, rix, riy, riz); return intersection; } /** Get a bounding box for this triangle. */ public BoundingBox getBounds() { double minx, maxx, miny, maxy, minz, maxz; Vec3 vert1 = tri.theMesh.vert[tri.v1]; Vec3 vert2 = tri.theMesh.vert[tri.v2]; Vec3 vert3 = tri.theMesh.vert[tri.v3]; minx = maxx = vert1.x; miny = maxy = vert1.y; minz = maxz = vert1.z; if (vert2.x < minx) minx = vert2.x; if (vert2.x > maxx) maxx = vert2.x; if (vert2.y < miny) miny = vert2.y; if (vert2.y > maxy) maxy = vert2.y; if (vert2.z < minz) minz = vert2.z; if (vert2.z > maxz) maxz = vert2.z; if (vert3.x < minx) minx = vert3.x; if (vert3.x > maxx) maxx = vert3.x; if (vert3.y < miny) miny = vert3.y; if (vert3.y > maxy) maxy = vert3.y; if (vert3.z < minz) minz = vert3.z; if (vert3.z > maxz) maxz = vert3.z; return new BoundingBox(minx, maxx, miny, maxy, minz, maxz); } /** Determine whether any part of the triangle lies within a bounding box. */ public boolean intersectsBox(BoundingBox bb) { Vec3 vert1 = tri.theMesh.vert[tri.v1]; Vec3 vert2 = tri.theMesh.vert[tri.v2]; Vec3 vert3 = tri.theMesh.vert[tri.v3]; // First see if any vertex is inside the box. if (bb.contains(vert1) || bb.contains(vert2) || bb.contains(vert3)) return true; // If any edge intersects the box, return true. if (edgeIntersectsBox(vert1, vert2, bb) || edgeIntersectsBox(vert2, vert3, bb) || edgeIntersectsBox(vert3, vert1, bb)) return true; // None of the vertices is inside the box. However, it is possible that the // triangle cuts through the entire box. Check each of the diagonals of // the box to see if one intersects the triangle. Ray r = new Ray(null); Vec3 orig = r.getOrigin(), dir = r.getDirection(); double len; orig.set(bb.minx, bb.miny, bb.minz); dir.set(bb.maxx-bb.minx, bb.maxy-bb.miny, bb.maxz-bb.minz); len = dir.length(); dir.scale(1.0/len); SurfaceIntersection intersect = checkIntersection(r); if (intersect != SurfaceIntersection.NO_INTERSECTION && intersect.intersectionDist(0) < len) return true; orig.set(bb.maxx, bb.miny, bb.minz); dir.set(bb.minx-bb.maxx, bb.maxy-bb.miny, bb.maxz-bb.minz); len = dir.length(); dir.scale(1.0/len); intersect = checkIntersection(r); if (intersect != SurfaceIntersection.NO_INTERSECTION && intersect.intersectionDist(0) < len) return true; orig.set(bb.minx, bb.maxy, bb.minz); dir.set(bb.maxx-bb.minx, bb.miny-bb.maxy, bb.maxz-bb.minz); len = dir.length(); dir.scale(1.0/len); intersect = checkIntersection(r); if (intersect != SurfaceIntersection.NO_INTERSECTION && intersect.intersectionDist(0) < len) return true; orig.set(bb.minx, bb.miny, bb.maxz); dir.set(bb.maxx-bb.minx, bb.maxy-bb.miny, bb.minz-bb.maxz); len = dir.length(); dir.scale(1.0/len); intersect = checkIntersection(r); if (intersect != SurfaceIntersection.NO_INTERSECTION && intersect.intersectionDist(0) < len) return true; return false; } /** Determine whether a particular edge of the triangle intersects a bounding box. */ boolean edgeIntersectsBox(Vec3 p1, Vec3 p2, BoundingBox bb) { double t1, t2, mint = -Double.MAX_VALUE, maxt = Double.MAX_VALUE; double dirx = p2.x-p1.x, diry = p2.y-p1.y, dirz = p2.z-p1.z; double len = Math.sqrt(dirx*dirx + diry*diry + dirz*dirz); if (dirx == 0.0) { if (p1.x < bb.minx || p1.x > bb.maxx) return false; } else { t1 = (bb.minx-p1.x)*len/dirx; t2 = (bb.maxx-p1.x)*len/dirx; if (t1 < t2) { if (t1 > mint) mint = t1; if (t2 < maxt) maxt = t2; } else { if (t2 > mint) mint = t2; if (t1 < maxt) maxt = t1; } if (mint > maxt || mint > len || maxt < 0.0) return false; } if (diry == 0.0) { if (p1.y < bb.miny || p1.y > bb.maxy) return false; } else { t1 = (bb.miny-p1.y)*len/diry; t2 = (bb.maxy-p1.y)*len/diry; if (t1 < t2) { if (t1 > mint) mint = t1; if (t2 < maxt) maxt = t2; } else { if (t2 > mint) mint = t2; if (t1 < maxt) maxt = t1; } if (mint > maxt || mint > len || maxt < 0.0) return false; } if (dirz == 0.0) { if (p1.z < bb.minz || p1.z > bb.maxz) return false; } else { t1 = (bb.minz-p1.z)*len/dirz; t2 = (bb.maxz-p1.z)*len/dirz; if (t1 < t2) { if (t1 > mint) mint = t1; if (t2 < maxt) maxt = t2; } else { if (t2 > mint) mint = t2; if (t1 < maxt) maxt = t1; } if (mint > maxt || mint > len || maxt < 0.0) return false; } return true; } /** Get the transformation from world coordinates to the object's local coordinates. */ public Mat4 toLocal() { return toLocal; } /** Get the mesh this triangle is part of. */ public Object getObject() { return tri.theMesh; } /** * Inner class representing an intersection with an RTTriangle. */ public static class TriangleIntersection implements SurfaceIntersection { private RTTriangleLowMemory rtTri; private double dist, u, v, rix, riy, riz; public TriangleIntersection() { } public void init(RTTriangleLowMemory rtTri, double dist, double u, double v, double rix, double riy, double riz) { this.rtTri = rtTri; this.dist = dist; this.u = u; this.v = v; this.rix = rix; this.riy = riy; this.riz = riz; } public RTObject getObject() { return rtTri; } public int numIntersections() { return 1; } public void intersectionPoint(int n, Vec3 p) { p.set(rix, riy, riz); } public double intersectionDist(int n) { return dist; } public void intersectionProperties(TextureSpec spec, Vec3 n, Vec3 viewDir, double size, double time) { double w = 1.0-u-v; if ((rtTri.flags&INTERP_NORMALS) == 0) n.set(rtTri.tri.theMesh.faceNorm[rtTri.tri.index]); else { Vec3 normals[] = rtTri.tri.theMesh.norm; Vec3 norm1 = normals[rtTri.tri.n1]; Vec3 norm2 = normals[rtTri.tri.n2]; Vec3 norm3 = normals[rtTri.tri.n3]; n.x = u*norm1.x + v*norm2.x + w*norm3.x; n.y = u*norm1.y + v*norm2.y + w*norm3.y; n.z = u*norm1.z + v*norm2.z + w*norm3.z; n.normalize(); } rtTri.tri.getTextureSpec(spec, -n.dot(viewDir), u, v, w, size, time); if ((rtTri.flags&BUMP_MAPPED) != 0) { rtTri.fromLocal.transformDirection(spec.bumpGrad); n.scale(spec.bumpGrad.dot(n)+1.0); n.subtract(spec.bumpGrad); n.normalize(); } } public void intersectionTransparency(int n, RGBColor trans, double angle, double size, double time) { rtTri.tri.getTransparency(trans, angle, u, v, 1.0-u-v, size, time); } public void trueNormal(Vec3 n) { n.set(rtTri.tri.theMesh.faceNorm[rtTri.tri.index]); } } }

Loading feature diagnosis…

Source regions

Feature contributions

Feature contributions

FeatureValueContribution
(log-odds)
Halstead volumeHow much symbolic information the code contains. It combines the total number of operators and values with the number of distinct ones.20872.069−688.778
Source linesThe number of non-empty source lines.436+174.4
Byte entropyHow varied the bytes in the source text are. Repeated bytes give a lower value; a more even mixture gives a higher value.4.746−7.12

Intercept 8.87 + feature contributions = -512.628 (log-odds).
Score = sigmoid(-512.628) = 0.

Score0.668

Feature contributions

FeatureValueContribution
(log-odds)
Comment layout frequencyHow frequently the layout switches between lines containing only comments or whitespace and lines containing code.436−14.401
Indentation frequencyHow rapidly indentation changes from line to line.414+13.583
Number layout frequencyHow rapidly the number of numeric values per line changes through the code.414−9.079
Identifier layout (vertical)How rapidly the visual pattern of identifier characters changes from top to bottom.434.942+5.67
Identifier layout (horizontal)How rapidly the visual pattern of identifier characters changes from left to right. It measures spatial frequency, not the meaning of the names.135.972−2.094
Comment layout (horizontal)How rapidly the visual pattern of comment characters changes from left to right.135.986+1.39
Operator visual areaThe share of the code’s visual area occupied by operators such as +, =, and *.0.118−0.207

Intercept 0.07 + feature contributions = -5.07 (log-odds).
Score = sigmoid(-5.07) = 0.006.

Score0.789
Score265
Run 1

The code has a clear overall structure with well-organized classes and methods, but it suffers from significant readability issues. The checkIntersection method is excessively long (over 50 lines) and contains complex mathematical operations that lack explanatory comments. The switch statement for dropAxis cases duplicates similar logic, making it harder to follow. There's heavy use of single-letter variable names (v, w, u, t, v0, vd) that obscure meaning. The edgeIntersectsBox method has deeply nested conditional logic (3-4 levels) making the flow hard to track. The getBounds method contains repetitive min/max comparisons that could be extracted into helper methods. While the code follows consistent formatting and has good Javadoc documentation, the naming conventions and method lengths significantly reduce readability. The action granularity is mixed—some areas have one operation per line while others pack multiple operations. The reading flow is disrupted by the need to mentally track many temporary variables through complex geometric calculations.

Run 2

The code is organized and shows clear intent, but it suffers from several readability issues. The constructor mixes setup logic like normal direction checks and drop-axis selection in ways that require careful reading. Intersection testing is long and has duplicated math across a switch statement. The edge-box test and bounding box methods feature repeated code blocks and deep, similar-looking conditionals. Some lines are extremely long and combine multiple operations, reducing readability. Naming is generally meaningful, but the use of short variables like 'u', 'v', 'w', and 'rix' and abbreviations like 'tri' is not always self-explanatory. Comments exist but are sparse, with complex geometric logic lacking explanation. The class is not unnecessarily long, but the repetition and terse identifiers make it harder to follow. Overall, it’s functional but not highly readable without domain knowledge.

Run 3

The code is fairly readable in terms of structure and naming, but it suffers from long methods, mathematical complexity, and repetitive logic. Methods like checkIntersection and edgeIntersectsBox mix multiple responsibilities and use many intermediate variables, reducing clarity. Nesting is moderate but the bounding-box intersection code repeats nearly identical blocks four times, making it verbose. Intent is generally clear from method names and comments, but the numerical operations obscure the underlying geometric logic. Action granularity is adequate, though multiple expressions are packed into single lines in several places. Reading flow is natural in simple getters but becomes dense in the geometric core. Overall, the code is maintainable for domain experts but less approachable for general readers.

Run 1

1. Code Structure: Responsibilities are logically separated into intersection, bounding-box, mapping, and intersection-result methods, though several geometric routines could use smaller helpers. 2. Nesting: Mostly shallow, aided by early returns; edgeIntersectsBox has repetitive nested conditionals. 3. Clarity of intent: Method names, documentation, and explanatory comments establish purpose, but terse mathematical variables, bit flags, and dense expressions require domain knowledge. 4. Code length: Reasonable for its functionality, but repeated axis checks, bounding comparisons, and box-diagonal tests add avoidable length. 5. Action granularity: Most statements perform one action per line; combined declarations, chained assignments, and inline conditional increments reduce consistency. 6. Reading flow: Operations generally follow a natural geometric sequence, with useful comments marking phases. Inconsistent brace indentation, long lines, repeated field-access chains, and limited spacing around operators interrupt otherwise clear flow.

Run 2

Code Structure: Responsibilities are logically separated into intersection, bounds, box testing, and surface-property methods, with a cohesive inner intersection class. Nesting: Mostly shallow thanks to early returns, although edgeIntersectsBox contains repetitive, moderately nested branches. Clarity of intent: Method names and explanatory comments communicate geometric goals well; abbreviated variables, numeric axis identifiers, dense formulas, and long field-access chains obscure implementation details. Code length: Considerable duplication in bounds calculations, diagonal checks, and axis clipping makes several methods unnecessarily long. Action granularity: Most statements perform one action per line, but combined declarations, chained assignments, and inline conditional increments reduce clarity. Reading flow: The overall progression is natural, with useful comments and whitespace, but inconsistent brace indentation, sparse operator spacing, and long expressions interrupt scanning.

Run 3

1. Code Structure: Responsibilities are logically separated into intersection, bounds, box testing, and intersection-data methods, with a cohesive inner class. 2. Nesting: Most methods use early returns and shallow control flow, but edgeIntersectsBox has several nested conditionals. 3. Clarity of intent: Method names, documentation, and explanatory comments establish purpose; abbreviated variables and dense geometric formulas require careful interpretation. 4. Code length: Repeated axis checks, bounding calculations, and diagonal tests make the implementation longer than necessary and could benefit from helper methods. 5. Action granularity: Most statements perform one action per line, although combined declarations, chained assignments, and inline condition/increment statements reduce consistency. 6. Reading flow: Methods generally progress naturally from setup through checks to results. However, inconsistent brace indentation, tightly spaced arithmetic, long expressions, and repeated deep field access interrupt scanning.