[Bf-blender-cvs] [994eb1ec17e] master: Cycles: support rendering new Volume object type

Brecht Van Lommel noreply at git.blender.org
Wed Mar 18 11:23:44 CET 2020


Commit: 994eb1ec17efc6d0a035356d04354bfc97bf8077
Author: Brecht Van Lommel
Date:   Tue Mar 17 16:52:14 2020 +0100
Branches: master
https://developer.blender.org/rB994eb1ec17efc6d0a035356d04354bfc97bf8077

Cycles: support rendering new Volume object type

Voxels are loaded directly from the OpenVDB grid. Rendering still only supports
dense grid, so memory usage is not great for sparse volumes, this is to be
addressed in the future.

Ref T73201

===================================================================

M	intern/cycles/CMakeLists.txt
M	intern/cycles/app/CMakeLists.txt
M	intern/cycles/blender/CMakeLists.txt
M	intern/cycles/blender/blender_geometry.cpp
M	intern/cycles/blender/blender_object.cpp
M	intern/cycles/blender/blender_sync.cpp
M	intern/cycles/blender/blender_volume.cpp
M	intern/cycles/render/CMakeLists.txt
A	intern/cycles/render/image_vdb.cpp
A	intern/cycles/render/image_vdb.h
M	intern/cycles/test/CMakeLists.txt

===================================================================

diff --git a/intern/cycles/CMakeLists.txt b/intern/cycles/CMakeLists.txt
index 6d4d2e38e82..024a94ea437 100644
--- a/intern/cycles/CMakeLists.txt
+++ b/intern/cycles/CMakeLists.txt
@@ -350,17 +350,6 @@ if(WITH_CYCLES_NETWORK)
   add_definitions(-DWITH_NETWORK)
 endif()
 
-if(WITH_OPENCOLORIO)
-  add_definitions(-DWITH_OCIO)
-  include_directories(
-    SYSTEM
-    ${OPENCOLORIO_INCLUDE_DIRS}
-  )
-  if(WIN32)
-    add_definitions(-DOpenColorIO_STATIC)
-  endif()
-endif()
-
 if(WITH_CYCLES_STANDALONE OR WITH_CYCLES_NETWORK OR WITH_CYCLES_CUBIN_COMPILER)
   add_subdirectory(app)
 endif()
diff --git a/intern/cycles/app/CMakeLists.txt b/intern/cycles/app/CMakeLists.txt
index 199ab8ce316..ef374f91a65 100644
--- a/intern/cycles/app/CMakeLists.txt
+++ b/intern/cycles/app/CMakeLists.txt
@@ -60,6 +60,7 @@ link_directories(
   ${TIFF_LIBPATH}
   ${OPENEXR_LIBPATH}
   ${OPENJPEG_LIBPATH}
+  ${OPENVDB_LIBPATH}
 )
 
 if(WITH_OPENCOLORIO)
diff --git a/intern/cycles/blender/CMakeLists.txt b/intern/cycles/blender/CMakeLists.txt
index ae191b6c0f7..496e8e9310b 100644
--- a/intern/cycles/blender/CMakeLists.txt
+++ b/intern/cycles/blender/CMakeLists.txt
@@ -92,6 +92,20 @@ if(WITH_MOD_FLUID)
   add_definitions(-DWITH_FLUID)
 endif()
 
+if(WITH_NEW_OBJECT_TYPES)
+  add_definitions(-DWITH_NEW_OBJECT_TYPES)
+endif()
+
+if(WITH_OPENVDB)
+  add_definitions(-DWITH_OPENVDB ${OPENVDB_DEFINITIONS})
+  list(APPEND INC_SYS
+    ${OPENVDB_INCLUDE_DIRS}
+  )
+  list(APPEND LIB
+    ${OPENVDB_LIBRARIES}
+  )
+endif()
+
 blender_add_lib(bf_intern_cycles "${SRC}" "${INC}" "${INC_SYS}" "${LIB}")
 
 # avoid link failure with clang 3.4 debug
diff --git a/intern/cycles/blender/blender_geometry.cpp b/intern/cycles/blender/blender_geometry.cpp
index e2a4a125ca1..ac5bae4bc66 100644
--- a/intern/cycles/blender/blender_geometry.cpp
+++ b/intern/cycles/blender/blender_geometry.cpp
@@ -38,7 +38,8 @@ Geometry *BlenderSync::sync_geometry(BL::Depsgraph &b_depsgraph,
   BL::ID b_key_id = (BKE_object_is_modified(b_ob)) ? b_ob_instance : b_ob_data;
   GeometryKey key(b_key_id.ptr.data, use_particle_hair);
   BL::Material material_override = view_layer.material_override;
-  Shader *default_shader = scene->default_surface;
+  Shader *default_shader = (b_ob.type() == BL::Object::type_VOLUME) ? scene->default_volume :
+                                                                      scene->default_surface;
   Geometry::Type geom_type = (use_particle_hair &&
                               (scene->curve_system_manager->primitive != CURVE_TRIANGLES)) ?
                                  Geometry::HAIR :
@@ -124,7 +125,7 @@ Geometry *BlenderSync::sync_geometry(BL::Depsgraph &b_depsgraph,
   if (use_particle_hair) {
     sync_hair(b_depsgraph, b_ob, geom, used_shaders);
   }
-  else if (object_fluid_gas_domain_find(b_ob)) {
+  else if (b_ob.type() == BL::Object::type_VOLUME || object_fluid_gas_domain_find(b_ob)) {
     Mesh *mesh = static_cast<Mesh *>(geom);
     sync_volume(b_ob, mesh, used_shaders);
   }
@@ -164,7 +165,7 @@ void BlenderSync::sync_geometry_motion(BL::Depsgraph &b_depsgraph,
   if (use_particle_hair) {
     sync_hair_motion(b_depsgraph, b_ob, geom, motion_step);
   }
-  else if (object_fluid_gas_domain_find(b_ob)) {
+  else if (b_ob.type() == BL::Object::type_VOLUME || object_fluid_gas_domain_find(b_ob)) {
     /* No volume motion blur support yet. */
   }
   else {
diff --git a/intern/cycles/blender/blender_object.cpp b/intern/cycles/blender/blender_object.cpp
index 334c25cafe1..48d309c259b 100644
--- a/intern/cycles/blender/blender_object.cpp
+++ b/intern/cycles/blender/blender_object.cpp
@@ -67,10 +67,16 @@ bool BlenderSync::object_is_mesh(BL::Object &b_ob)
     return false;
   }
 
-  if (b_ob.type() == BL::Object::type_CURVE) {
+  BL::Object::type_enum type = b_ob.type();
+
+  if (type == BL::Object::type_VOLUME) {
+    /* Will be exported attached to mesh. */
+    return true;
+  }
+  else if (type == BL::Object::type_CURVE) {
     /* Skip exporting curves without faces, overhead can be
      * significant if there are many for path animation. */
-    BL::Curve b_curve(b_ob.data());
+    BL::Curve b_curve(b_ob_data);
 
     return (b_curve.bevel_object() || b_curve.extrude() != 0.0f || b_curve.bevel_depth() != 0.0f ||
             b_curve.dimensions() == BL::Curve::dimensions_2D || b_ob.modifiers.length());
diff --git a/intern/cycles/blender/blender_sync.cpp b/intern/cycles/blender/blender_sync.cpp
index 4529c6a2798..3d932825ae7 100644
--- a/intern/cycles/blender/blender_sync.cpp
+++ b/intern/cycles/blender/blender_sync.cpp
@@ -178,6 +178,11 @@ void BlenderSync::sync_recalc(BL::Depsgraph &b_depsgraph, BL::SpaceView3D &b_v3d
         world_recalc = true;
       }
     }
+    /* Volume */
+    else if (b_id.is_a(&RNA_Volume)) {
+      BL::Volume b_volume(b_id);
+      geometry_map.set_recalc(b_volume);
+    }
   }
 
   BlenderViewportParameters new_viewport_parameters(b_v3d);
diff --git a/intern/cycles/blender/blender_volume.cpp b/intern/cycles/blender/blender_volume.cpp
index 7f393fcb819..ee64796b393 100644
--- a/intern/cycles/blender/blender_volume.cpp
+++ b/intern/cycles/blender/blender_volume.cpp
@@ -16,12 +16,19 @@
 
 #include "render/colorspace.h"
 #include "render/image.h"
+#include "render/image_vdb.h"
 #include "render/mesh.h"
 #include "render/object.h"
 
 #include "blender/blender_sync.h"
 #include "blender/blender_util.h"
 
+#ifdef WITH_OPENVDB
+#  include <openvdb/openvdb.h>
+openvdb::GridBase::ConstPtr BKE_volume_grid_openvdb_for_read(const struct Volume *volume,
+                                                             struct VolumeGrid *grid);
+#endif
+
 CCL_NAMESPACE_BEGIN
 
 /* TODO: verify this is not loading unnecessary attributes. */
@@ -210,19 +217,121 @@ static void sync_smoke_volume(Scene *scene, BL::Object &b_ob, Mesh *mesh, float
 
     attr->data_voxel() = scene->image_manager->add_image(loader, params);
   }
+}
 
-  /* Create a matrix to transform from object space to mesh texture space.
-   * This does not work with deformations but that can probably only be done
-   * well with a volume grid mapping of coordinates. */
-  if (mesh->need_attribute(scene, ATTR_STD_GENERATED_TRANSFORM)) {
-    Attribute *attr = mesh->attributes.add(ATTR_STD_GENERATED_TRANSFORM);
-    Transform *tfm = attr->data_transform();
+class BlenderVolumeLoader : public VDBImageLoader {
+ public:
+  BlenderVolumeLoader(BL::Volume b_volume, const string &grid_name)
+      : VDBImageLoader(grid_name),
+        b_volume(b_volume),
+        b_volume_grid(PointerRNA_NULL),
+        unload(false)
+  {
+#ifdef WITH_OPENVDB
+    /* Find grid with matching name. */
+    BL::Volume::grids_iterator b_grid_iter;
+    for (b_volume.grids.begin(b_grid_iter); b_grid_iter != b_volume.grids.end(); ++b_grid_iter) {
+      if (b_grid_iter->name() == grid_name) {
+        b_volume_grid = *b_grid_iter;
+      }
+    }
+#endif
+  }
 
-    BL::Mesh b_mesh(b_ob.data());
-    float3 loc, size;
-    mesh_texture_space(b_mesh, loc, size);
+  bool load_metadata(ImageMetaData &metadata) override
+  {
+    if (!b_volume_grid) {
+      return false;
+    }
+
+    unload = !b_volume_grid.is_loaded();
+
+#ifdef WITH_OPENVDB
+    Volume *volume = (Volume *)b_volume.ptr.data;
+    VolumeGrid *volume_grid = (VolumeGrid *)b_volume_grid.ptr.data;
+    grid = BKE_volume_grid_openvdb_for_read(volume, volume_grid);
+#endif
+
+    return VDBImageLoader::load_metadata(metadata);
+  }
+
+  bool load_pixels(const ImageMetaData &metadata,
+                   void *pixels,
+                   const size_t pixel_size,
+                   const bool associate_alpha) override
+  {
+    if (!b_volume_grid) {
+      return false;
+    }
+
+    return VDBImageLoader::load_pixels(metadata, pixels, pixel_size, associate_alpha);
+  }
 
-    *tfm = transform_translate(-loc) * transform_scale(size);
+  bool equals(const ImageLoader &other) const override
+  {
+    /* TODO: detect multiple volume datablocks with the same filepath. */
+    const BlenderVolumeLoader &other_loader = (const BlenderVolumeLoader &)other;
+    return b_volume == other_loader.b_volume && b_volume_grid == other_loader.b_volume_grid;
+  }
+
+  void cleanup() override
+  {
+    VDBImageLoader::cleanup();
+    if (b_volume_grid && unload) {
+      b_volume_grid.unload();
+    }
+  }
+
+  BL::Volume b_volume;
+  BL::VolumeGrid b_volume_grid;
+  bool unload;
+};
+
+static void sync_volume_object(BL::BlendData &b_data, BL::Object &b_ob, Scene *scene, Mesh *mesh)
+{
+  BL::Volume b_volume(b_ob.data());
+  b_volume.grids.load(b_data.ptr.data);
+
+  mesh->volume_isovalue = 1e-3f; /* TODO: make user setting. */
+
+  /* Find grid with matching name. */
+  BL::Volume::grids_iterator b_grid_iter;
+  for (b_volume.grids.begin(b_grid_iter); b_grid_iter != b_volume.grids.end(); ++b_grid_iter) {
+    BL::VolumeGrid b_grid = *b_grid_iter;
+    ustring name = ustring(b_grid.name());
+    AttributeStandard std = ATTR_STD_NONE;
+
+    if (name == Attribute::standard_name(ATTR_STD_VOLUME_DENSITY)) {
+      std = ATTR_STD_VOLUME_DENSITY;
+    }
+    else if (name == Attribute::standard_name(ATTR_STD_VOLUME_COLOR)) {
+      std = ATTR_STD_VOLUME_COLOR;
+    }
+    else if (name == Attribute::standard_name(ATTR_STD_VOLUME_FLAME)) {
+      std = ATTR_STD_VOLUME_FLAME;
+    }
+    else if (name == Attribute::standard_name(ATTR_STD_VOLUME_HEAT)) {
+      std = ATTR_STD_VOLUME_HEAT;
+    }
+    else if (name == Attribute::standard_name(ATTR_STD_VOLUME_TEMPERATURE)) {
+      std = ATTR_STD_VOLUME_TEMPERATURE;
+    }
+    else if (name == Attribute::standard_name(ATTR_STD_VOLUME_VELOCITY)) {
+      std = ATTR_STD_VOLUME_VELOCITY;
+    }
+
+    if ((std != ATTR_STD_NONE && mesh->need_attribute(scene, std)) ||
+        mesh->need_attribute(scene, name)) {
+      Attribute *attr = (std != ATTR_STD_NONE) ?
+                            mesh->attributes.add(std) :
+                            mesh->attributes.add(name, TypeDesc::TypeFloat, ATTR_ELEMENT_VOXEL);
+
+      ImageLoader *loader = new BlenderVolumeLoader(b_volume, name.string());
+      ImageParams params;
+      params.frame = b_volume.grids.frame();
+
+      attr->data_voxel() = scene->image_manager->add_image(loader, params);
+    }
   

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list