oatz
03-06-2008, 02:48 PM
I recently watched the talk Bobo gave on voxel approach to large data sets from Siggraph 2006.
I wanted to use this approach to help me with a LOD system by finding the items that were nearest to the camera. The scene setup is dead simple: A box Defining the bounds of the voxel system. A camera, and then three spheres all within the box.
Here is my script:
clearListener()
voxelGrid = #()
(
local thecamera = $camera01
local voxelBounds = $Box01
local voxelUnit = 25
local objArray = $sphere*
local tier = 1
fn getVoxelAddress origin pos =
(
local theAddress = (pos-origin)/voxelUnit
[1+(ceil theAddress.x) as integer, 1+(ceil theAddress.y) as integer, 1+(ceil theAddress.z) as integer ]
)
fn VoxelGrid_BuildVoxelGrid =
(
local grid_x = ceil ((voxelBounds.max.x - voxelBounds.min.x)/VoxelUnit) as integer + 1
local grid_y = ceil ((voxelBounds.max.y - voxelBounds.min.y)/VoxelUnit) as integer + 1
local grid_z = ceil ((voxelBounds.max.z - voxelBounds.min.z)/VoxelUnit) as integer + 1
format "Grid % % %\n" grid_x grid_y grid_z
for z = 1 to grid_z do
(
VoxelGrid[z] = #()
for y = 1 to grid_y do
(
VoxelGrid[z][y] = #()
for x = 1 to grid_x do
(
VoxelGrid[z][y][x] = #()
--format "Z :% \n Y:% \n X:% \n" z y x
)--end x
)--end y
)--endz
for i= 1 to objArray.count do
(
theAddress = getVoxelAddress voxelBounds.min objArray[i].position
append VoxelGrid[theAddress.z][theAddress.y][theAddress.x] i
format "Appending value : % to address %\n" i theAddress
)
format "\nVG : %\nCount : %\n" VoxelGrid VoxelGrid.count
)--end fn
fn findClosestObj pos =
(
local st = timestamp()
local minDist = 99999
local closestObj = 0
local thePos = [0,0,0]
local theAddress = getVoxelAddress voxelBounds.min pos
format "Camera Address : %\n" theAddress
for z = theAddress.z-tier to theAddress.z+tier do
(
for y = theAddress.y-tier to theAddress.y+tier do
(
for x = theAddress.x-tier to theAddress.x+tier do
(
try
(
for v in theVoxelGrid[z][y][x] do
(
thePos = objArray[v].pos
format "Position Test %\n" thePos
format "V:% \n" v
if (theDist = distance thePos pos) < minDist then
(
minDist = theDist
closestObj = v
)
)--end v loop
)catch()
)--end x loop
)--end y loop
)--end z loop
print closestObj
if closestObj > 0 do select objArray[closestObj]
)--end fn
-----call functions
VoxelGrid_BuildVoxelGrid()
findClosestObj thecamera.pos
)--end local
It works fine until the testing in the V loop. For some reason it fails every time. Even when the camera and a sphere are in teh identical voxel, it won't give me a result.
I've spent too long working it over. I think I've lost perspective on it. Any fresh eyes would help. Thanks!
Khye
I wanted to use this approach to help me with a LOD system by finding the items that were nearest to the camera. The scene setup is dead simple: A box Defining the bounds of the voxel system. A camera, and then three spheres all within the box.
Here is my script:
clearListener()
voxelGrid = #()
(
local thecamera = $camera01
local voxelBounds = $Box01
local voxelUnit = 25
local objArray = $sphere*
local tier = 1
fn getVoxelAddress origin pos =
(
local theAddress = (pos-origin)/voxelUnit
[1+(ceil theAddress.x) as integer, 1+(ceil theAddress.y) as integer, 1+(ceil theAddress.z) as integer ]
)
fn VoxelGrid_BuildVoxelGrid =
(
local grid_x = ceil ((voxelBounds.max.x - voxelBounds.min.x)/VoxelUnit) as integer + 1
local grid_y = ceil ((voxelBounds.max.y - voxelBounds.min.y)/VoxelUnit) as integer + 1
local grid_z = ceil ((voxelBounds.max.z - voxelBounds.min.z)/VoxelUnit) as integer + 1
format "Grid % % %\n" grid_x grid_y grid_z
for z = 1 to grid_z do
(
VoxelGrid[z] = #()
for y = 1 to grid_y do
(
VoxelGrid[z][y] = #()
for x = 1 to grid_x do
(
VoxelGrid[z][y][x] = #()
--format "Z :% \n Y:% \n X:% \n" z y x
)--end x
)--end y
)--endz
for i= 1 to objArray.count do
(
theAddress = getVoxelAddress voxelBounds.min objArray[i].position
append VoxelGrid[theAddress.z][theAddress.y][theAddress.x] i
format "Appending value : % to address %\n" i theAddress
)
format "\nVG : %\nCount : %\n" VoxelGrid VoxelGrid.count
)--end fn
fn findClosestObj pos =
(
local st = timestamp()
local minDist = 99999
local closestObj = 0
local thePos = [0,0,0]
local theAddress = getVoxelAddress voxelBounds.min pos
format "Camera Address : %\n" theAddress
for z = theAddress.z-tier to theAddress.z+tier do
(
for y = theAddress.y-tier to theAddress.y+tier do
(
for x = theAddress.x-tier to theAddress.x+tier do
(
try
(
for v in theVoxelGrid[z][y][x] do
(
thePos = objArray[v].pos
format "Position Test %\n" thePos
format "V:% \n" v
if (theDist = distance thePos pos) < minDist then
(
minDist = theDist
closestObj = v
)
)--end v loop
)catch()
)--end x loop
)--end y loop
)--end z loop
print closestObj
if closestObj > 0 do select objArray[closestObj]
)--end fn
-----call functions
VoxelGrid_BuildVoxelGrid()
findClosestObj thecamera.pos
)--end local
It works fine until the testing in the V loop. For some reason it fails every time. Even when the camera and a sphere are in teh identical voxel, it won't give me a result.
I've spent too long working it over. I think I've lost perspective on it. Any fresh eyes would help. Thanks!
Khye
