diff --git a/minetest.lua b/minetest.lua index 2cf101a..cc8e336 100644 --- a/minetest.lua +++ b/minetest.lua @@ -263,42 +263,6 @@ function get_liquid_flow_direction(pos) return dir end ---+ Möller-Trumbore -function ray_triangle_intersection(origin, direction, triangle) - local point_1, point_2, point_3 = unpack(triangle) - local edge_1, edge_2 = vector.subtract(point_2, point_1), vector.subtract(point_3, point_1) - local h = vector.cross(direction, edge_2) - local a = vector.dot(edge_1, h) - if math.abs(a) < 1e-9 then - return - end - local f = 1 / a - local diff = vector.subtract(origin, point_1) - local u = f * vector.dot(diff, h) - if u < 0 or u > 1 then - return - end - local q = vector.cross(diff, edge_1) - local v = f * vector.dot(direction, q) - if v < 0 or u + v > 1 then - return - end - local pos_on_line = f * vector.dot(edge_2, q); - if pos_on_line >= 0 then - return pos_on_line - end -end - -function triangle_normal(triangle) - local point_1, point_2, point_3 = unpack(triangle) - local edge_1, edge_2 = vector.subtract(point_2, point_1), vector.subtract(point_3, point_1) - return vector.normalize{ - x = edge_1.y * edge_2.z - edge_1.z * edge_2.y, - y = edge_1.z * edge_2.x - edge_1.x * edge_2.z, - z = edge_1.x * edge_2.y - edge_1.y * edge_2.x - } -end - --+ Raycast wrapper with proper flowingliquid intersections function raycast(pos1, pos2, objects, liquids) local raycast = minetest.raycast(pos1, pos2, objects, liquids) @@ -415,10 +379,10 @@ function raycast(pos1, pos2, objects, liquids) {corner_levels[1], corner_levels[2], corner_levels[3]}, {corner_levels[1], corner_levels[3], corner_levels[4]} } do - local pos_on_ray = ray_triangle_intersection(relative, direction, triangle) + local pos_on_ray = modlib.vector.ray_triangle_intersection(relative, direction, triangle) if pos_on_ray and pos_on_ray <= length then pointed_thing.intersection_point = vector.add(pos1, vector.multiply(direction, pos_on_ray)) - pointed_thing.intersection_normal = vector.multiply(triangle_normal(triangle), -1) + pointed_thing.intersection_normal = vector.multiply(modlib.vector.triangle_normal(triangle), -1) return pointed_thing end end diff --git a/vector.lua b/vector.lua index 23b43f2..66da123 100644 --- a/vector.lua +++ b/vector.lua @@ -85,4 +85,40 @@ function box_box_collision(diff, box, other_box) end end return true +end + +--+ Möller-Trumbore +function ray_triangle_intersection(origin, direction, triangle) + local point_1, point_2, point_3 = unpack(triangle) + local edge_1, edge_2 = vector.subtract(point_2, point_1), vector.subtract(point_3, point_1) + local h = vector.cross(direction, edge_2) + local a = vector.dot(edge_1, h) + if math.abs(a) < 1e-9 then + return + end + local f = 1 / a + local diff = vector.subtract(origin, point_1) + local u = f * vector.dot(diff, h) + if u < 0 or u > 1 then + return + end + local q = vector.cross(diff, edge_1) + local v = f * vector.dot(direction, q) + if v < 0 or u + v > 1 then + return + end + local pos_on_line = f * vector.dot(edge_2, q); + if pos_on_line >= 0 then + return pos_on_line + end +end + +function triangle_normal(triangle) + local point_1, point_2, point_3 = unpack(triangle) + local edge_1, edge_2 = vector.subtract(point_2, point_1), vector.subtract(point_3, point_1) + return vector.normalize{ + x = edge_1.y * edge_2.z - edge_1.z * edge_2.y, + y = edge_1.z * edge_2.x - edge_1.x * edge_2.z, + z = edge_1.x * edge_2.y - edge_1.y * edge_2.x + } end \ No newline at end of file