Toshihiro Shimizu 890ddd
#include <cmath> // pow()</cmath>
Toshihiro Shimizu 890ddd
#include "iwa_noise1234.h"
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
namespace
Toshihiro Shimizu 890ddd
{
Toshihiro Shimizu 890ddd
double perlin_noise_3d_(
Toshihiro Shimizu 890ddd
	const double x, const double y, const double z, const int octaves_start // 0<=
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int octaves_end // 0<=
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const double persistence // Not 0
Toshihiro Shimizu 890ddd
							 // 1/4 or 1/2 or 1/sqrt(3) or 1/sqrt(2) or 1 or ...
Toshihiro Shimizu 890ddd
	)
Toshihiro Shimizu 890ddd
{
Toshihiro Shimizu 890ddd
	double total = 0;
Toshihiro Shimizu 890ddd
	Noise1234 pn;
Toshihiro Shimizu 890ddd
	for (int ii = octaves_start; ii <= octaves_end; ++ii) {
Toshihiro Shimizu 890ddd
		const double frequency = pow(2.0, ii); //1,2,4,8...
Toshihiro Shimizu 890ddd
		const double amplitude = pow(persistence, ii);
Toshihiro Shimizu 890ddd
		total += pn.noise(
Toshihiro Shimizu 890ddd
					 x * frequency, y * frequency, z * frequency) *
Toshihiro Shimizu 890ddd
				 amplitude;
Toshihiro Shimizu 890ddd
	}
Toshihiro Shimizu 890ddd
	return total;
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
double perlin_noise_minmax_(
Toshihiro Shimizu 890ddd
	const int octaves_start // 0<=
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int octaves_end // 0<=
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const double persistence // Not 0
Toshihiro Shimizu 890ddd
							 // 1/4 or 1/2 or 1/sqrt(3) or 1/sqrt(2) or 1 or ...
Toshihiro Shimizu 890ddd
	)
Toshihiro Shimizu 890ddd
{
Toshihiro Shimizu 890ddd
	double total = 0;
Toshihiro Shimizu 890ddd
	for (int ii = octaves_start; ii <= octaves_end; ++ii) {
Toshihiro Shimizu 890ddd
		total += pow(persistence, ii);
Toshihiro Shimizu 890ddd
	}
Toshihiro Shimizu 890ddd
	return total;
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
//--------------------------------------------------------------------
Toshihiro Shimizu 890ddd
#include <stdexcept>		// std::domain_error(-)</stdexcept>
Toshihiro Shimizu 890ddd
#include <limits>			// std::numeric_limits</limits>
Toshihiro Shimizu 890ddd
#include "igs_ifx_common.h" /* igs::image::rgba */
Toshihiro Shimizu 890ddd
#include "igs_perlin_noise.h"
Toshihiro Shimizu 890ddd
namespace
Toshihiro Shimizu 890ddd
{
Toshihiro Shimizu 890ddd
template <class t=""></class>
Toshihiro Shimizu 890ddd
void change_(
Toshihiro Shimizu 890ddd
	T *image_array, const int height // pixel
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int width // pixel
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int channels, const bool alpha_rendering_sw, const double a11 // geometry of 2D affine transformation
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const double a12, const double a13, const double a21, const double a22, const double a23, const double zz, const int octaves_start // 0<=
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int octaves_end // 0<=
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const double persistence // Not 0
Toshihiro Shimizu 890ddd
	)
Toshihiro Shimizu 890ddd
{
Toshihiro Shimizu 890ddd
	const int max_div = std::numeric_limits<t>::max();</t>
Toshihiro Shimizu 890ddd
	const int max_div_2 = max_div / 2;
Toshihiro Shimizu 890ddd
	// 255 / 2    --> 127
Toshihiro Shimizu 890ddd
	// 65535 / 2  --> 32767
Toshihiro Shimizu 890ddd
	//const double max_mul = static_cast<double>(max_div_2+0.999999);</double>
Toshihiro Shimizu 890ddd
	//const double max_off = static_cast<double>(max_div_2+1);</double>
Toshihiro Shimizu 890ddd
	const double max_mul = static_cast<double>(max_div_2 + 0.499999);</double>
Toshihiro Shimizu 890ddd
	const double max_off = static_cast<double>(max_div_2 + 1.5);</double>
Toshihiro Shimizu 890ddd
	/*
Toshihiro Shimizu 890ddd
	-1 .............. 0 ......... 1
Toshihiro Shimizu 890ddd
	x127+0.499999
Toshihiro Shimizu 890ddd
	------------------------------------------
Toshihiro Shimizu 890ddd
	-127+0.499999 ... 0 ......... 127+0.499999
Toshihiro Shimizu 890ddd
	+127+1.5      ... 127+1.5 ... 127+1.5
Toshihiro Shimizu 890ddd
	------------------------------------------
Toshihiro Shimizu 890ddd
	1.000001 ........ 127+1.5 ... 255.999999
Toshihiro Shimizu 890ddd
	integer
Toshihiro Shimizu 890ddd
	------------------------------------------
Toshihiro Shimizu 890ddd
	1 ............... 128 ....... 255
Toshihiro Shimizu 890ddd
*/
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
	const double maxi = perlin_noise_minmax_(
Toshihiro Shimizu 890ddd
		octaves_start, octaves_end, persistence);
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
	using namespace igs::image::rgba;
Toshihiro Shimizu 890ddd
	T *image_crnt = image_array;
Toshihiro Shimizu 890ddd
	for (int yy = 0; yy < height; ++yy) {
Toshihiro Shimizu 890ddd
		for (int xx = 0; xx < width; ++xx, image_crnt += channels) {
Toshihiro Shimizu 890ddd
			const T val = static_cast<t>(perlin_noise_3d_(</t>
Toshihiro Shimizu 890ddd
											 xx * a11 + yy * a12 + a13, xx * a21 + yy * a22 + a23, zz, octaves_start, octaves_end, persistence) /
Toshihiro Shimizu 890ddd
											 maxi * max_mul +
Toshihiro Shimizu 890ddd
										 max_off);
Toshihiro Shimizu 890ddd
			for (int zz = 0; zz < channels; ++zz) {
Toshihiro Shimizu 890ddd
				if (!alpha_rendering_sw && (alp == zz)) {
Toshihiro Shimizu 890ddd
					image_crnt[zz] = static_cast<t>(max_div);</t>
Toshihiro Shimizu 890ddd
				} else {
Toshihiro Shimizu 890ddd
					image_crnt[zz] = val;
Toshihiro Shimizu 890ddd
				}
Toshihiro Shimizu 890ddd
			}
Toshihiro Shimizu 890ddd
		}
Toshihiro Shimizu 890ddd
	}
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
// #include "igs_geometry2d.h"
Toshihiro Shimizu 890ddd
void igs::perlin_noise::change(
Toshihiro Shimizu 890ddd
	unsigned char *image_array, const int height // pixel
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int width // pixel
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int channels, const int bits, const bool alpha_rendering_sw, const double a11 // geometry of 2D affine transformation
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const double a12, const double a13, const double a21, const double a22, const double a23, const double zz, const int octaves_start // 0...
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const int octaves_end // 0...
Toshihiro Shimizu 890ddd
	,
Toshihiro Shimizu 890ddd
	const double persistence // not 0
Toshihiro Shimizu 890ddd
	)
Toshihiro Shimizu 890ddd
{
Toshihiro Shimizu 890ddd
	// igs::geometry2d::affine af(a11 , a12 , a13 , a21 , a22 , a23);
Toshihiro Shimizu 890ddd
	// igs::geometry2d::translate();
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
	if (std::numeric_limits<unsigned char="">::digits == bits) {</unsigned>
Toshihiro Shimizu 890ddd
		change_(
Toshihiro Shimizu 890ddd
			image_array, height, width, channels, alpha_rendering_sw, a11, a12, a13, a21, a22, a23, zz, octaves_start, octaves_end, persistence);
Toshihiro Shimizu 890ddd
	} else if (std::numeric_limits<unsigned short="">::digits == bits) {</unsigned>
Toshihiro Shimizu 890ddd
		change_(
Toshihiro Shimizu 890ddd
			reinterpret_cast<unsigned *="" short="">(image_array), height, width, channels, alpha_rendering_sw, a11, a12, a13, a21, a22, a23, zz, octaves_start, octaves_end, persistence);</unsigned>
Toshihiro Shimizu 890ddd
	} else {
Toshihiro Shimizu 890ddd
		throw std::domain_error("Bad bits,Not uchar/ushort");
Toshihiro Shimizu 890ddd
	}
Toshihiro Shimizu 890ddd
}