def intersect_light(pos, d, tmax): hit, t, _ = ray_aabb_intersection(light_min_pos, light_max_pos, pos, d) if hit and 0 < t < tmax: hit = 1 else: hit = 0 t = inf return hit, t
def dda(eye_pos, d_): d = d_ for i in ti.static(range(3)): if ti.abs(d[i]) < 1e-6: d[i] = 1e-6 rinv = 1.0 / d rsign = ti.Vector([0, 0, 0]) for i in ti.static(range(3)): if d[i] > 0: rsign[i] = 1 else: rsign[i] = -1 bbox_min = ti.Vector([0.0, 0.0, 0.0]) - 10 * eps bbox_max = ti.Vector([1.0, 1.0, 1.0]) + 10 * eps inter, near, far = ray_aabb_intersection(bbox_min, bbox_max, eye_pos, d) hit_distance = inf normal = ti.Vector([0.0, 0.0, 0.0]) c = ti.Vector([0.0, 0.0, 0.0]) if inter: near = ti.max(0, near) pos = eye_pos + d * (near + 5 * eps) o = grid_resolution * pos ipos = ti.Matrix.floor(o).cast(ti.i32) dis = (ipos - o + 0.5 + rsign * 0.5) * rinv running = 1 i = 0 hit_pos = ti.Vector([0.0, 0.0, 0.0]) while running: last_sample = query_density_int(ipos) if not inside_grid_loose(ipos): running = 0 # normal = [0, 0, 0] if last_sample: mini = (ipos - o + ti.Vector([0.5, 0.5, 0.5]) - rsign * 0.5) * rinv hit_distance = mini.max() * (1 / grid_resolution) + near hit_pos = eye_pos + hit_distance * d c = voxel_color(hit_pos) running = 0 else: mm = ti.Vector([0, 0, 0]) if dis[0] <= dis[1] and dis[0] < dis[2]: mm[0] = 1 elif dis[1] <= dis[0] and dis[1] <= dis[2]: mm[1] = 1 else: mm[2] = 1 dis += mm * rsign * rinv ipos += mm * rsign normal = -mm * rsign i += 1 return hit_distance, normal, c
def dda_voxel(self, eye_pos, d): for i in ti.static(range(3)): if abs(d[i]) < 1e-6: d[i] = 1e-6 rinv = 1.0 / d rsign = ti.Vector([0, 0, 0]) for i in ti.static(range(3)): if d[i] > 0: rsign[i] = 1 else: rsign[i] = -1 bbox_min = self.bbox[0] bbox_max = self.bbox[1] inter, near, far = ray_aabb_intersection(bbox_min, bbox_max, eye_pos, d) hit_distance = inf normal = ti.Vector([0.0, 0.0, 0.0]) c = ti.Vector([0.0, 0.0, 0.0]) if inter: near = max(0, near) pos = eye_pos + d * (near + 5 * eps) o = self.voxel_inv_dx * pos ipos = int(ti.floor(o)) dis = (ipos - o + 0.5 + rsign * 0.5) * rinv running = 1 i = 0 hit_pos = ti.Vector([0.0, 0.0, 0.0]) while running: last_sample = int(self.query_density(ipos)) if not self.inside_particle_grid(ipos): running = 0 if last_sample: mini = (ipos - o + ti.Vector([0.5, 0.5, 0.5]) - rsign * 0.5) * rinv hit_distance = mini.max() * self.voxel_dx + near hit_pos = eye_pos + hit_distance * d c = self.voxel_color(hit_pos) running = 0 else: mm = ti.Vector([0, 0, 0]) if dis[0] <= dis[1] and dis[0] < dis[2]: mm[0] = 1 elif dis[1] <= dis[0] and dis[1] <= dis[2]: mm[1] = 1 else: mm[2] = 1 dis += mm * rsign * rinv ipos += mm * rsign normal = -mm * rsign i += 1 return hit_distance, normal, c
def dda_particle(eye_pos, d_, t): grid_res = particle_grid_res bbox_min = bbox[0] bbox_max = bbox[1] hit_pos = ti.Vector([0.0, 0.0, 0.0]) normal = ti.Vector([0.0, 0.0, 0.0]) c = ti.Vector([0.0, 0.0, 0.0]) d = d_ for i in ti.static(range(3)): if ti.abs(d[i]) < 1e-6: d[i] = 1e-6 inter, near, far = ray_aabb_intersection(bbox_min, bbox_max, eye_pos, d) near = ti.max(0, near) closest_intersection = inf if inter: pos = eye_pos + d * (near + eps) rinv = 1.0 / d rsign = ti.Vector([0, 0, 0]) for i in ti.static(range(3)): if d[i] > 0: rsign[i] = 1 else: rsign[i] = -1 o = grid_res * pos ipos = ti.Matrix.floor(o).cast(ti.i32) dis = (ipos - o + 0.5 + rsign * 0.5) * rinv running = 1 while running: inside = inside_particle_grid(ipos) if inside: num_particles = voxel_has_particle[ipos] if num_particles != 0: num_particles = ti.length(pid.parent(), ipos) for k in range(num_particles): p = pid[ipos[0], ipos[1], ipos[2], k] v = particle_v[p] x = particle_x[p] + t * v color = particle_color[p] dist, poss = intersect_sphere(eye_pos, d, x, sphere_radius) hit_pos = poss if dist < closest_intersection and dist > 0: hit_pos = eye_pos + dist * d closest_intersection = dist normal = ti.Matrix.normalized(hit_pos - x) c = [ color // 256**2 / 255.0, color / 256 % 256 / 255.0, color % 256 / 255.0 ] else: running = 0 normal = [0, 0, 0] if closest_intersection < inf: running = 0 else: # hits nothing. Continue ray marching mm = ti.Vector([0, 0, 0]) if dis[0] <= dis[1] and dis[0] <= dis[2]: mm[0] = 1 elif dis[1] <= dis[0] and dis[1] <= dis[2]: mm[1] = 1 else: mm[2] = 1 dis += mm * rsign * rinv ipos += mm * rsign return closest_intersection, normal, c
def dda_particle(eye_pos, d, t): grid_res = particle_grid_res # bounding box bbox_min = bbox[0] bbox_max = bbox[1] hit_pos = ti.Vector([0.0, 0.0, 0.0]) normal = ti.Vector([0.0, 0.0, 0.0]) c = ti.Vector([0.0, 0.0, 0.0]) for i in ti.static(range(3)): if abs(d[i]) < 1e-6: d[i] = 1e-6 inter, near, far = ray_aabb_intersection(bbox_min, bbox_max, eye_pos, d) near = max(0, near) closest_intersection = inf if inter: pos = eye_pos + d * (near + eps) rinv = 1.0 / d rsign = ti.Vector([0, 0, 0]) for i in ti.static(range(3)): if d[i] > 0: rsign[i] = 1 else: rsign[i] = -1 o = grid_res * pos ipos = ti.floor(o).cast(int) dis = (ipos - o + 0.5 + rsign * 0.5) * rinv running = 1 # DDA for voxels with at least one particle while running: inside = inside_particle_grid(ipos) if inside: # once we actually intersect with a voxel that contains at least one particle, loop over the particle list num_particles = voxel_has_particle[ipos] if num_particles != 0: num_particles = ti.length(pid.parent(), ipos) for k in range(num_particles): p = pid[ipos[0], ipos[1], ipos[2], k] v = particle_v[p] x = particle_x[p] + t * v color = particle_color[p] # ray-sphere intersection dist, poss = intersect_sphere(eye_pos, d, x, sphere_radius) hit_pos = poss if dist < closest_intersection and dist > 0: hit_pos = eye_pos + dist * d closest_intersection = dist normal = (hit_pos - x).normalized() c = color else: running = 0 normal = [0, 0, 0] if closest_intersection < inf: running = 0 else: # hits nothing. Continue ray marching mm = ti.Vector([0, 0, 0]) if dis[0] <= dis[1] and dis[0] <= dis[2]: mm[0] = 1 elif dis[1] <= dis[0] and dis[1] <= dis[2]: mm[1] = 1 else: mm[2] = 1 dis += mm * rsign * rinv ipos += mm * rsign return closest_intersection, normal, c
def intersect_light(pos, d): intersect, tmin, _ = ray_aabb_intersection(lihgt_min_pos, light_max_pos, pos, d) if tmin < 0 or intersect == 0: tmin = inf return tmin
def dda_particle(eye_pos, d, t, step): bbox_min = bbox[0] bbox_max = bbox[1] hit_pos = ti.Vector([0.0, 0.0, 0.0]) normal = ti.Vector([0.0, 0.0, 0.0]) c = ti.Vector([0.0, 0.0, 0.0]) for i in ti.static(range(3)): if abs( d[i] ) < 1e-6: #iterating over three components of direction vector from rayCast func d[i] = 1e-6 #assigning a lower bound to direction vec components... not sure why? inter, near, far = ray_aabb_intersection(bbox_min, bbox_max, eye_pos, d) #findimg near = max(0, near) closest_intersection = inf # print(closest_intersection) if inter: pos = eye_pos + d * (near + eps) rinv = 1.0 / d rsign = ti.Vector([0, 0, 0]) for i in ti.static(range(3)): if d[i] > 0: rsign[i] = 1 else: rsign[i] = -1 # o = (particle_grid_res * pos)/ 10.0 o = world_to_grid(pos) # o = grid_res * pos ipos = ti.Matrix.floor(o).cast(int) dis = (ipos - o + 0.5 + rsign * 0.5) * rinv running = 1 num = 999999999 num2 = 2000000002 # DDA for voxels with at least one particle while running: inside = inside_particle_grid(ipos) if inside: # print(ipos[0]) # print(ipos[1]) # print(ipos[2]) # once we actually intersect with a voxel that contains at least one particle, loop over the particle list num_particles = voxel_has_particle[ipos] if num_particles != 0: # print(num) # print(num_particles) # world_pos = grid_to_world(ipos) # print(world_pos[0]) # print(world_pos[1]) # print(world_pos[2]) num_particles = ti.length(pid.parent(), ipos) for k in range(num_particles): # print(num2) p = pid[ipos[0], ipos[1], ipos[2], k] # v = mpm.v[p] # x = mpm.x[p] + step * mpm.v[p] x = mpm.x[p] # print(x[0]) # print(x[1]) # print(x[2]) # print(d[0]) # print(d[1]) # print(d[2]) dist, poss = intersect_sphere(eye_pos, d, x, sphere_radius) # print(num) # print(dist) hit_pos = poss if dist < closest_intersection and dist > 0: hit_pos = eye_pos + dist * d closest_intersection = dist normal = ti.Matrix.normalized(hit_pos - x) else: running = 0 normal = [0, 0, 0] if closest_intersection < inf: # print(num) running = 0 else: # print(num2) # hits nothing. Continue ray marching mm = ti.Vector([0, 0, 0]) if dis[0] <= dis[1] and dis[0] <= dis[2]: mm[0] = 1 elif dis[1] <= dis[0] and dis[1] <= dis[2]: mm[1] = 1 else: mm[2] = 1 dis += mm * rsign * rinv ipos += mm * rsign return closest_intersection, normal