mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-03 02:15:43 -04:00
PfmFile::set_no_data_nan() and related methods
This commit is contained in:
parent
1885ccdb97
commit
a38de91fbd
@ -59,13 +59,13 @@ has_point(int x, int y) const {
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::get_component
|
||||
// Function: PfmFile::get_channel
|
||||
// Access: Published
|
||||
// Description: Returns the cth component of the point value at the
|
||||
// Description: Returns the cth channel of the point value at the
|
||||
// indicated point.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE PN_float32 PfmFile::
|
||||
get_component(int x, int y, int c) const {
|
||||
get_channel(int x, int y, int c) const {
|
||||
nassertr(x >= 0 && x < _x_size &&
|
||||
y >= 0 && y < _y_size &&
|
||||
c >= 0 && c < _num_channels, 0.0f);
|
||||
@ -73,13 +73,13 @@ get_component(int x, int y, int c) const {
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::set_component
|
||||
// Function: PfmFile::set_channel
|
||||
// Access: Published
|
||||
// Description: Replaces the cth component of the point value at the
|
||||
// Description: Replaces the cth channel of the point value at the
|
||||
// indicated point.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE void PfmFile::
|
||||
set_component(int x, int y, int c, PN_float32 value) {
|
||||
set_channel(int x, int y, int c, PN_float32 value) {
|
||||
nassertv(x >= 0 && x < _x_size &&
|
||||
y >= 0 && y < _y_size &&
|
||||
c >= 0 && c < _num_channels);
|
||||
@ -470,8 +470,7 @@ set_zero_special(bool zero_special) {
|
||||
// Description: Sets the no_data_chan4 flag. When this flag is true,
|
||||
// and the pfm file has 4 channels, then a negative
|
||||
// value in the fourth channel indicates no data. When
|
||||
// it is false, a zero or positive value in the fourth
|
||||
// channel indicates valid data.
|
||||
// it is false, all points are valid.
|
||||
//
|
||||
// This is a special case of set_no_data_value().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -479,7 +478,7 @@ INLINE void PfmFile::
|
||||
set_no_data_chan4(bool chan4) {
|
||||
if (chan4 && _num_channels == 4) {
|
||||
_has_no_data_value = true;
|
||||
_no_data_value = LPoint4f::zero();
|
||||
_no_data_value.set(0.0, 0.0, 0.0, -1.0);
|
||||
_has_point = has_point_chan4;
|
||||
} else {
|
||||
clear_no_data_value();
|
||||
|
@ -520,6 +520,95 @@ fill(const LPoint4f &value) {
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::fill_nan
|
||||
// Access: Published
|
||||
// Description: Fills the table with all NaN.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
fill_nan() {
|
||||
PN_float32 nan = make_nan((PN_float32)0.0);
|
||||
LPoint4f nan4(nan, nan, nan, nan);
|
||||
fill(nan4);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::fill_no_data_value
|
||||
// Access: Published
|
||||
// Description: Fills the table with the current no_data value, so
|
||||
// that the table is empty.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
fill_no_data_value() {
|
||||
fill(_no_data_value);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::fill_channel
|
||||
// Access: Published
|
||||
// Description: Fills the indicated channel with all of the same
|
||||
// value, leaving the other channels unchanged.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
fill_channel(int channel, PN_float32 value) {
|
||||
nassertv(channel >= 0 && channel < _num_channels);
|
||||
|
||||
for (int yi = 0; yi < _y_size; ++yi) {
|
||||
for (int xi = 0; xi < _x_size; ++xi) {
|
||||
_table[(yi * _x_size + xi) * _num_channels + channel] = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::fill_channel_nan
|
||||
// Access: Published
|
||||
// Description: Fills the indicated channel with NaN, leaving the
|
||||
// other channels unchanged.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
fill_channel_nan(int channel) {
|
||||
PN_float32 nan = make_nan((PN_float32)0.0);
|
||||
fill_channel(channel, nan);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::fill_channel_masked
|
||||
// Access: Published
|
||||
// Description: Fills the indicated channel with all of the same
|
||||
// value, but only where the table already has a data
|
||||
// point. Leaves empty points unchanged.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
fill_channel_masked(int channel, PN_float32 value) {
|
||||
nassertv(channel >= 0 && channel < _num_channels);
|
||||
|
||||
if (!_has_no_data_value) {
|
||||
fill_channel(channel, value);
|
||||
} else {
|
||||
for (int yi = 0; yi < _y_size; ++yi) {
|
||||
for (int xi = 0; xi < _x_size; ++xi) {
|
||||
if (has_point(xi, yi)) {
|
||||
_table[(yi * _x_size + xi) * _num_channels + channel] = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::fill_channel_masked_nan
|
||||
// Access: Published
|
||||
// Description: Fills the indicated channel with NaN, but only where
|
||||
// the table already has a data point. Leaves empty
|
||||
// points unchanged.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
fill_channel_masked_nan(int channel) {
|
||||
PN_float32 nan = make_nan((PN_float32)0.0);
|
||||
fill_channel_masked(channel, nan);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::calc_average_point
|
||||
// Access: Published
|
||||
@ -792,6 +881,48 @@ is_column_empty(int x, int y_begin, int y_end) const {
|
||||
return true;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::set_no_data_nan
|
||||
// Access: Published
|
||||
// Description: Sets the no_data_nan flag. When num_channels is
|
||||
// nonzero, then a NaN value in any of the first
|
||||
// num_channels channels indicates no data for that
|
||||
// point. If num_channels is zero, then all points are
|
||||
// valid.
|
||||
//
|
||||
// This is a special case of set_no_data_value().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void PfmFile::
|
||||
set_no_data_nan(int num_channels) {
|
||||
if (num_channels > 0) {
|
||||
num_channels = min(num_channels, _num_channels);
|
||||
_has_no_data_value = true;
|
||||
_no_data_value = LPoint4f::zero();
|
||||
PN_float32 nan = make_nan((PN_float32)0.0);
|
||||
for (int i = 0; i < num_channels; ++i) {
|
||||
_no_data_value[i] = nan;
|
||||
}
|
||||
switch (num_channels) {
|
||||
case 1:
|
||||
_has_point = has_point_nan_1;
|
||||
break;
|
||||
case 2:
|
||||
_has_point = has_point_nan_2;
|
||||
break;
|
||||
case 3:
|
||||
_has_point = has_point_nan_3;
|
||||
break;
|
||||
case 4:
|
||||
_has_point = has_point_nan_4;
|
||||
break;
|
||||
default:
|
||||
nassertv(false);
|
||||
}
|
||||
} else {
|
||||
clear_no_data_value();
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::set_no_data_value
|
||||
// Access: Published
|
||||
@ -806,6 +937,9 @@ set_no_data_value(const LPoint4f &no_data_value) {
|
||||
case 1:
|
||||
_has_point = has_point_1;
|
||||
break;
|
||||
case 2:
|
||||
_has_point = has_point_2;
|
||||
break;
|
||||
case 3:
|
||||
_has_point = has_point_3;
|
||||
break;
|
||||
@ -838,6 +972,9 @@ resize(int new_x_size, int new_y_size) {
|
||||
|
||||
PfmFile result;
|
||||
result.clear(new_x_size, new_y_size, _num_channels);
|
||||
if (_has_no_data_value) {
|
||||
result.fill(_no_data_value);
|
||||
}
|
||||
|
||||
if (pfm_resize_gaussian) {
|
||||
result.gaussian_filter_from(pfm_resize_radius, *this);
|
||||
@ -1284,7 +1421,7 @@ copy_channel(int to_channel, const PfmFile &other, int from_channel) {
|
||||
|
||||
for (int yi = 0; yi < _y_size; ++yi) {
|
||||
for (int xi = 0; xi < _x_size; ++xi) {
|
||||
set_component(xi, yi, to_channel, other.get_component(xi, yi, from_channel));
|
||||
set_channel(xi, yi, to_channel, other.get_channel(xi, yi, from_channel));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -2010,6 +2147,21 @@ has_point_1(const PfmFile *self, int x, int y) {
|
||||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::has_point_2
|
||||
// Access: Private, Static
|
||||
// Description: The implementation of has_point() for 2-component
|
||||
// files with a no_data_value.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool PfmFile::
|
||||
has_point_2(const PfmFile *self, int x, int y) {
|
||||
if ((x >= 0 && x < self->_x_size) &&
|
||||
(y >= 0 && y < self->_y_size)) {
|
||||
return *(LPoint2f *)&self->_table[(y * self->_x_size + x) * 2] != *(LPoint2f *)&self->_no_data_value;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::has_point_3
|
||||
// Access: Private, Static
|
||||
@ -2055,3 +2207,67 @@ has_point_chan4(const PfmFile *self, int x, int y) {
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::has_point_nan_1
|
||||
// Access: Private, Static
|
||||
// Description: The implementation of has_point() for
|
||||
// files with set_no_data_nan() in effect. This means
|
||||
// that the data is valid iff no components involve NaN.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool PfmFile::
|
||||
has_point_nan_1(const PfmFile *self, int x, int y) {
|
||||
if ((x >= 0 && x < self->_x_size) &&
|
||||
(y >= 0 && y < self->_y_size)) {
|
||||
return !cnan(self->_table[(y * self->_x_size + x) * self->_num_channels]);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::has_point_nan_2
|
||||
// Access: Private, Static
|
||||
// Description: The implementation of has_point() for
|
||||
// files with set_no_data_nan() in effect. This means
|
||||
// that the data is valid iff no components involve NaN.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool PfmFile::
|
||||
has_point_nan_2(const PfmFile *self, int x, int y) {
|
||||
if ((x >= 0 && x < self->_x_size) &&
|
||||
(y >= 0 && y < self->_y_size)) {
|
||||
return !((LVecBase2f *)&self->_table[(y * self->_x_size + x) * self->_num_channels])->is_nan();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::has_point_nan_3
|
||||
// Access: Private, Static
|
||||
// Description: The implementation of has_point() for
|
||||
// files with set_no_data_nan() in effect. This means
|
||||
// that the data is valid iff no components involve NaN.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool PfmFile::
|
||||
has_point_nan_3(const PfmFile *self, int x, int y) {
|
||||
if ((x >= 0 && x < self->_x_size) &&
|
||||
(y >= 0 && y < self->_y_size)) {
|
||||
return !((LVecBase3f *)&self->_table[(y * self->_x_size + x) * self->_num_channels])->is_nan();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: PfmFile::has_point_nan_4
|
||||
// Access: Private, Static
|
||||
// Description: The implementation of has_point() for
|
||||
// files with set_no_data_nan() in effect. This means
|
||||
// that the data is valid iff no components involve NaN.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool PfmFile::
|
||||
has_point_nan_4(const PfmFile *self, int x, int y) {
|
||||
if ((x >= 0 && x < self->_x_size) &&
|
||||
(y >= 0 && y < self->_y_size)) {
|
||||
return !((LVecBase4f *)&self->_table[(y * self->_x_size + x) * self->_num_channels])->is_nan();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
@ -57,8 +57,8 @@ PUBLISHED:
|
||||
INLINE void set_scale(PN_float32 scale);
|
||||
|
||||
INLINE bool has_point(int x, int y) const;
|
||||
INLINE PN_float32 get_component(int x, int y, int c) const;
|
||||
INLINE void set_component(int x, int y, int c, PN_float32 value);
|
||||
INLINE PN_float32 get_channel(int x, int y, int c) const;
|
||||
INLINE void set_channel(int x, int y, int c, PN_float32 value);
|
||||
INLINE PN_float32 get_point1(int x, int y) const;
|
||||
INLINE void set_point1(int x, int y, PN_float32 point);
|
||||
INLINE const LPoint2f &get_point2(int x, int y) const;
|
||||
@ -82,6 +82,12 @@ PUBLISHED:
|
||||
INLINE void fill(const LPoint2f &value);
|
||||
INLINE void fill(const LPoint3f &value);
|
||||
void fill(const LPoint4f &value);
|
||||
void fill_nan();
|
||||
void fill_no_data_value();
|
||||
void fill_channel(int channel, PN_float32 value);
|
||||
void fill_channel_nan(int channel);
|
||||
void fill_channel_masked(int channel, PN_float32 value);
|
||||
void fill_channel_masked_nan(int channel);
|
||||
|
||||
BLOCKING bool calc_average_point(LPoint3f &result, PN_float32 x, PN_float32 y, PN_float32 radius) const;
|
||||
BLOCKING bool calc_bilinear_point(LPoint3f &result, PN_float32 x, PN_float32 y) const;
|
||||
@ -95,6 +101,7 @@ PUBLISHED:
|
||||
|
||||
INLINE void set_zero_special(bool zero_special);
|
||||
INLINE void set_no_data_chan4(bool chan4);
|
||||
void set_no_data_nan(int num_channels);
|
||||
void set_no_data_value(const LPoint4f &no_data_value);
|
||||
INLINE void set_no_data_value(const LPoint4d &no_data_value);
|
||||
INLINE void clear_no_data_value();
|
||||
@ -169,9 +176,14 @@ private:
|
||||
|
||||
static bool has_point_noop(const PfmFile *file, int x, int y);
|
||||
static bool has_point_1(const PfmFile *file, int x, int y);
|
||||
static bool has_point_2(const PfmFile *file, int x, int y);
|
||||
static bool has_point_3(const PfmFile *file, int x, int y);
|
||||
static bool has_point_4(const PfmFile *file, int x, int y);
|
||||
static bool has_point_chan4(const PfmFile *file, int x, int y);
|
||||
static bool has_point_nan_1(const PfmFile *file, int x, int y);
|
||||
static bool has_point_nan_2(const PfmFile *file, int x, int y);
|
||||
static bool has_point_nan_3(const PfmFile *file, int x, int y);
|
||||
static bool has_point_nan_4(const PfmFile *file, int x, int y);
|
||||
|
||||
private:
|
||||
typedef vector_float Table;
|
||||
|
@ -94,9 +94,11 @@ FUNCTION_NAME(IMAGETYPE &dest, const IMAGETYPE &source,
|
||||
filter, filter_width);
|
||||
|
||||
for (b = 0; b < dest.BSIZE(); b++) {
|
||||
if (temp_dest_weight[b] != 0) {
|
||||
dest.SETVAL(a, b, channel, (double)temp_dest[b]/(double)source_max);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
PANDA_FREE_ARRAY(temp_dest);
|
||||
PANDA_FREE_ARRAY(temp_dest_weight);
|
||||
|
@ -555,8 +555,8 @@ gaussian_filter_from(double width, const PNMImage ©) {
|
||||
#define IMAGETYPE PfmFile
|
||||
#define ASIZE get_x_size
|
||||
#define BSIZE get_y_size
|
||||
#define GETVAL(a, b, channel) get_component(a, b, channel)
|
||||
#define SETVAL(a, b, channel, v) set_component(a, b, channel, v)
|
||||
#define GETVAL(a, b, channel) get_channel(a, b, channel)
|
||||
#define SETVAL(a, b, channel, v) set_channel(a, b, channel, v)
|
||||
#include "pnm-image-filter-core.cxx"
|
||||
#undef SETVAL
|
||||
#undef GETVAL
|
||||
@ -569,8 +569,8 @@ gaussian_filter_from(double width, const PNMImage ©) {
|
||||
#define IMAGETYPE PfmFile
|
||||
#define ASIZE get_y_size
|
||||
#define BSIZE get_x_size
|
||||
#define GETVAL(a, b, channel) get_component(b, a, channel)
|
||||
#define SETVAL(a, b, channel, v) set_component(b, a, channel, v)
|
||||
#define GETVAL(a, b, channel) get_channel(b, a, channel)
|
||||
#define SETVAL(a, b, channel, v) set_channel(b, a, channel, v)
|
||||
#include "pnm-image-filter-core.cxx"
|
||||
#undef SETVAL
|
||||
#undef GETVAL
|
||||
@ -585,8 +585,8 @@ gaussian_filter_from(double width, const PNMImage ©) {
|
||||
#define ASIZE get_x_size
|
||||
#define BSIZE get_y_size
|
||||
#define HASVAL(a, b) has_point(a, b)
|
||||
#define GETVAL(a, b, channel) get_component(a, b, channel)
|
||||
#define SETVAL(a, b, channel, v) set_component(a, b, channel, v)
|
||||
#define GETVAL(a, b, channel) get_channel(a, b, channel)
|
||||
#define SETVAL(a, b, channel, v) set_channel(a, b, channel, v)
|
||||
#include "pnm-image-filter-sparse-core.cxx"
|
||||
#undef SETVAL
|
||||
#undef GETVAL
|
||||
@ -601,8 +601,8 @@ gaussian_filter_from(double width, const PNMImage ©) {
|
||||
#define ASIZE get_y_size
|
||||
#define BSIZE get_x_size
|
||||
#define HASVAL(a, b) has_point(b, a)
|
||||
#define GETVAL(a, b, channel) get_component(b, a, channel)
|
||||
#define SETVAL(a, b, channel, v) set_component(b, a, channel, v)
|
||||
#define GETVAL(a, b, channel) get_channel(b, a, channel)
|
||||
#define SETVAL(a, b, channel, v) set_channel(b, a, channel, v)
|
||||
#include "pnm-image-filter-sparse-core.cxx"
|
||||
#undef SETVAL
|
||||
#undef GETVAL
|
||||
|
Loading…
x
Reference in New Issue
Block a user