Skip to content

[BUG] NaN handling in background change #1910

Open
@Xilef11

Description

@Xilef11

Environment

Operating System: Ubuntu 22.04
Version / Commit SHA: v9.1.0
Other: Using the Python bindings

Describe the bug

When setting the background value of a (Float) grid, if the previous background value was NaN, the values of all inactive voxels get changed to the new value.

To Reproduce

Example script:

import pyopenvdb as vdb
import math
import itertools

grid = vdb.FloatGrid()
grid.background = 0.0

accessor = grid.getAccessor()
# create a few blocks of active voxels
on_list = [(5,5,5), (-5,-5,-5)]
for coords in on_list:
    accessor.setValueOn(coords, 1.0)

# set a few off voxels
off_list = [(-2,-2,-2),(2,2,2)]
for coords in off_list:
    accessor.setValueOff(coords, 5.0)

# check values
unchanged = [(0,0,0)]
print("** initial values **")
for coords in itertools.chain(on_list, off_list, unchanged):
    print(f"Voxel {coords} is {accessor.probeValue(coords)}")

# change background
grid.background = -1.0
print("** after background change to -1.0 **")  # here, our custom inactive voxels are still at 5.0
# check values
for coords in itertools.chain(on_list, off_list, unchanged):
    print(f"Voxel {coords} is {accessor.probeValue(coords)}")

# change background again
grid.background = math.nan
print("** after background change to nan **")  # still at 5.0
# check values
for coords in itertools.chain(on_list, off_list, unchanged):
    print(f"Voxel {coords} is {accessor.probeValue(coords)}")

# change background again
grid.background = -12.0
print("** after background change to -12 **")  # changed from 5.0 to -12
# check values
for coords in itertools.chain(on_list, off_list, unchanged):
    print(f"Voxel {coords} is {accessor.probeValue(coords)}")

Output:

** initial values **
Voxel (5, 5, 5) is (1.0, True)
Voxel (-5, -5, -5) is (1.0, True)
Voxel (-2, -2, -2) is (5.0, False)
Voxel (2, 2, 2) is (5.0, False)
Voxel (0, 0, 0) is (0.0, False)
** after background change to -1.0 **
Voxel (5, 5, 5) is (1.0, True)
Voxel (-5, -5, -5) is (1.0, True)
Voxel (-2, -2, -2) is (5.0, False)
Voxel (2, 2, 2) is (5.0, False)
Voxel (0, 0, 0) is (-1.0, False)
** after background change to nan **
Voxel (5, 5, 5) is (1.0, True)
Voxel (-5, -5, -5) is (1.0, True)
Voxel (-2, -2, -2) is (5.0, False)
Voxel (2, 2, 2) is (5.0, False)
Voxel (0, 0, 0) is (nan, False)
** after background change to -12 **
Voxel (5, 5, 5) is (1.0, True)
Voxel (-5, -5, -5) is (1.0, True)
Voxel (-2, -2, -2) is (-12.0, False)
Voxel (2, 2, 2) is (-12.0, False)
Voxel (0, 0, 0) is (-12.0, False)

Expected behavior

Inactive voxels with a value different from the previous background value should not be changed when the background value is changed. This is specified in the documentation of tools::changeBackground which gets called when setting grid.background through the Python API

Additional context

As a side note, it is unclear from the python API that setting grid.background will change the values (by calling tools::changeBackground) instead of setting a reference value. Understanding this behaviour required digging through the pyopenvdb source code.

&pyGrid::getGridBackground<GridType>, &pyGrid::setGridBackground<GridType>,

tools::changeBackground(grid.tree(), background);

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions