Geometry Nodes: Image Info Node

This commit adds a new "Image Info" node to retrieve various
information from an image like its width, height, and whether
it has an alpha channel. It is also possible to retrieve the FPS
and frame count of video files.

Differential Revision: https://developer.blender.org/D15042
This commit is contained in:
Iliya Katueshenock 2022-11-14 18:55:51 -06:00 committed by Hans Goudey
parent b64042b482
commit efcd587bc2
Notes: blender-bot 2023-02-14 11:07:28 +01:00
Referenced by issue #102531, AO node in Cycles can no longer be used for volume rendering.
7 changed files with 101 additions and 0 deletions

View File

@ -139,6 +139,7 @@ class NODE_MT_geometry_node_GEO_INPUT(Menu):
node_add_menu.add_node_type(layout, "FunctionNodeInputBool")
node_add_menu.add_node_type(layout, "GeometryNodeCollectionInfo")
node_add_menu.add_node_type(layout, "FunctionNodeInputColor")
node_add_menu.add_node_type(layout, "GeometryNodeImageInfo")
node_add_menu.add_node_type(layout, "FunctionNodeInputInt")
node_add_menu.add_node_type(layout, "GeometryNodeIsViewport")
node_add_menu.add_node_type(layout, "GeometryNodeInputMaterial")

View File

@ -1546,6 +1546,7 @@ struct TexResult;
#define GEO_NODE_MESH_TOPOLOGY_VERTEX_OF_CORNER 1186
#define GEO_NODE_SAMPLE_UV_SURFACE 1187
#define GEO_NODE_SET_CURVE_NORMAL 1188
#define GEO_NODE_IMAGE_INFO 1189
/** \} */

View File

@ -4753,6 +4753,7 @@ static void registerGeometryNodes()
register_node_type_geo_field_at_index();
register_node_type_geo_flip_faces();
register_node_type_geo_geometry_to_instance();
register_node_type_geo_image_info();
register_node_type_geo_image_texture();
register_node_type_geo_input_curve_handles();
register_node_type_geo_input_curve_tilt();

View File

@ -62,6 +62,7 @@ void register_node_type_geo_extrude_mesh(void);
void register_node_type_geo_field_at_index(void);
void register_node_type_geo_flip_faces(void);
void register_node_type_geo_geometry_to_instance(void);
void register_node_type_geo_image_info(void);
void register_node_type_geo_image_texture(void);
void register_node_type_geo_input_curve_handles(void);
void register_node_type_geo_input_curve_tilt(void);

View File

@ -319,6 +319,7 @@ DefNode(GeometryNode, GEO_NODE_FILL_CURVE, def_geo_curve_fill, "FILL_CURVE", Fil
DefNode(GeometryNode, GEO_NODE_FILLET_CURVE, def_geo_curve_fillet, "FILLET_CURVE", FilletCurve, "Fillet Curve", "Round corners by generating circular arcs on each control point")
DefNode(GeometryNode, GEO_NODE_FLIP_FACES, 0, "FLIP_FACES", FlipFaces, "Flip Faces", "Reverse the order of the vertices and edges of selected faces, flipping their normal direction")
DefNode(GeometryNode, GEO_NODE_GEOMETRY_TO_INSTANCE, 0, "GEOMETRY_TO_INSTANCE", GeometryToInstance, "Geometry to Instance", "Convert each input geometry into an instance, which can be much faster than the Join Geometry node when the inputs are large")
DefNode(GeometryNode, GEO_NODE_IMAGE_INFO, 0, "IMAGE_INFO", ImageInfo, "Image Info", "Retrieve information about an image")
DefNode(GeometryNode, GEO_NODE_IMAGE_TEXTURE, def_geo_image_texture, "IMAGE_TEXTURE", ImageTexture, "Image Texture", "Sample values from an image texture")
DefNode(GeometryNode, GEO_NODE_INPUT_CURVE_HANDLES, 0, "INPUT_CURVE_HANDLES", InputCurveHandlePositions,"Curve Handle Positions", "Retrieve the position of each Bézier control point's handles")
DefNode(GeometryNode, GEO_NODE_INPUT_CURVE_TILT, 0, "INPUT_CURVE_TILT", InputCurveTilt, "Curve Tilt", "Retrieve the angle at each control point used to twist the curve's normal around its tangent")

View File

@ -72,6 +72,7 @@ set(SRC
nodes/node_geo_field_at_index.cc
nodes/node_geo_flip_faces.cc
nodes/node_geo_geometry_to_instance.cc
nodes/node_geo_image_info.cc
nodes/node_geo_image_texture.cc
nodes/node_geo_input_curve_handles.cc
nodes/node_geo_input_curve_tilt.cc

View File

@ -0,0 +1,95 @@
/* SPDX-License-Identifier: GPL-2.0-or-later */
#include "BKE_image.h"
#include "BLI_path_util.h"
#include "IMB_colormanagement.h"
#include "IMB_imbuf.h"
#include "IMB_imbuf_types.h"
#include "UI_interface.h"
#include "UI_resources.h"
#include "node_geometry_util.hh"
namespace blender::nodes::node_geo_image_info_cc {
static void node_declare(NodeDeclarationBuilder &b)
{
b.add_input<decl::Image>(N_("Image")).hide_label();
b.add_input<decl::Int>(N_("Frame"))
.min(0)
.description(N_("Which frame to use for videos. Note that different frames in videos can "
"have different resolutions"));
b.add_output<decl::Int>(N_("Width"));
b.add_output<decl::Int>(N_("Height"));
b.add_output<decl::Bool>(N_("Has Alpha"))
.description(N_("Whether the image has an alpha channel"));
b.add_output<decl::Int>(N_("Frame Count"))
.description(N_("The number of animation frames. If a single image, then 1"));
b.add_output<decl::Float>(N_("FPS")).description(
N_("Animation playback speed in frames per second. If a single image, then 0"));
}
static void node_geo_exec(GeoNodeExecParams params)
{
Image *image = params.get_input<Image *>("Image");
const int frame = params.get_input<int>("Frame");
if (!image) {
params.set_default_remaining_outputs();
return;
}
ImageUser image_user;
BKE_imageuser_default(&image_user);
image_user.frames = INT_MAX;
image_user.framenr = BKE_image_is_animated(image) ? frame : 0;
void *lock;
ImBuf *ibuf = BKE_image_acquire_ibuf(image, &image_user, &lock);
BLI_SCOPED_DEFER([&]() { BKE_image_release_ibuf(image, ibuf, lock); });
if (!ibuf) {
params.set_default_remaining_outputs();
return;
}
params.set_output("Has Alpha", ELEM(ibuf->planes, 32, 16));
params.set_output("Width", ibuf->x);
params.set_output("Height", ibuf->y);
int frames = 1;
float fps = 0.0f;
if (ImageAnim *ianim = static_cast<ImageAnim *>(image->anims.first)) {
auto *anim = ianim->anim;
if (anim) {
frames = IMB_anim_get_duration(anim, IMB_TC_NONE);
short fps_sec = 0;
float fps_sec_base = 0.0f;
IMB_anim_get_fps(anim, &fps_sec, &fps_sec_base, true);
fps = float(fps_sec) / fps_sec_base;
}
}
params.set_output("Frame Count", frames);
params.set_output("FPS", fps);
}
} // namespace blender::nodes::node_geo_image_info_cc
void register_node_type_geo_image_info()
{
namespace file_ns = blender::nodes::node_geo_image_info_cc;
static bNodeType ntype;
geo_node_type_base(&ntype, GEO_NODE_IMAGE_INFO, "Image Info", NODE_CLASS_INPUT);
ntype.declare = file_ns::node_declare;
ntype.geometry_node_execute = file_ns::node_geo_exec;
node_type_size_preset(&ntype, NODE_SIZE_LARGE);
nodeRegisterType(&ntype);
}