Open mclarekin opened 4 years ago
ad a) it need to be implemented ad b) You can write inline functions. Example, where I defined absolute() function just before formula code:
/**
* Mandelbulber v2, a 3D fractal generator _%}}i*<. ____ _______
* Copyright (C) 2019 Mandelbulber Team _>]|=||i=i<, / __ \___ ___ ___ / ___/ /
* \><||i|=>>%) / /_/ / _ \/ -_) _ \/ /__/ /__
* This file is part of Mandelbulber. )<=i=]=|=i<> \____/ .__/\__/_//_/\___/____/
* The project is licensed under GPLv3, -<>>=|><|||` /_/
* see also COPYING file in this folder. ~+{i%+++
*
* Menger Sponge formula created by Knighty
* @reference
* http://www.fractalforums.com/ifs-iterated-function-systems/kaleidoscopic-(escape-time-ifs)/
* This file has been autogenerated by tools/populateUiInformation.php
* from the file "fractal_menger_sponge.cpp" in the folder formula/definition
* F E E L F R E E T O E D I T T H I S F I L E !
*/
float4 absolute(float4 in)
{
float4 out;
out.x = fabs(in.x);
out.y = fabs(in.y);
out.z = fabs(in.z);
out.w = fabs(in.w);
return out;
}
REAL4 CustomIteration(REAL4 z, __constant sFractalCl *fractal, sExtendedAuxCl *aux)
{
z = absolute(z);
if (z.x - z.y < 0.0f)
{
REAL temp = z.x;
z.x = z.y;
z.y = temp;
}
if (z.x - z.z < 0.0f)
{
REAL temp = z.x;
z.x = z.z;
z.z = temp;
}
if (z.y - z.z < 0.0f)
{
REAL temp = z.y;
z.y = z.z;
z.z = temp;
}
z *= fractal->transformCommon.scale3;
z.x -= 2.0f;
z.y -= 2.0f;
if (z.z > 1.0f) z.z -= 2.0f;
aux->DE *= fractal->transformCommon.scale3;
return z;
}
b) can i bring a parameter or an aux. into the inline function (i tried but failed)
I tried harder and could bring the parameter in :) so that is OK question is it possible to have inlines in the c++ setup?
You can use any parameters. See this example where I moved SphericalFold to separate function. It has several paremeters: z, r2, fractal and aux.
/**
* Mandelbulber v2, a 3D fractal generator _%}}i*<. ____ _______
* Copyright (C) 2020 Mandelbulber Team _>]|=||i=i<, / __ \___ ___ ___ / ___/ /
* \><||i|=>>%) / /_/ / _ \/ -_) _ \/ /__/ /__
* This file is part of Mandelbulber. )<=i=]=|=i<> \____/ .__/\__/_//_/\___/____/
* The project is licensed under GPLv3, -<>>=|><|||` /_/
* see also COPYING file in this folder. ~+{i%+++
*
* Mandelbox fractal known as AmazingBox or ABox, invented by Tom Lowe in 2010
* @reference
* http://www.fractalforums.com/ifs-iterated-function-systems/amazing-fractal/msg12467/#msg12467
* This formula contains aux.color
* This file has been autogenerated by tools/populateUiInformation.php
* from the file "fractal_mandelbox.cpp" in the folder formula/definition
* F E E L F R E E T O E D I T T H I S F I L E !
*/
REAL4 SphericalFold(REAL4 z, REAL r2, __constant sFractalCl *fractal, sExtendedAuxCl *aux)
{
if (r2 < fractal->mandelbox.mR2)
{
z *= fractal->mandelbox.mboxFactor1;
aux->DE *= fractal->mandelbox.mboxFactor1;
aux->color += fractal->mandelbox.color.factorSp1;
}
else if (r2 < fractal->mandelbox.fR2)
{
REAL tglad_factor2 = fractal->mandelbox.fR2 / r2;
z *= tglad_factor2;
aux->DE *= tglad_factor2;
aux->color += fractal->mandelbox.color.factorSp2;
}
return z;
}
REAL4 CustomIteration(REAL4 z, __constant sFractalCl *fractal, sExtendedAuxCl *aux)
{
if (fractal->mandelbox.rotationsEnabled)
{
REAL4 zRot;
// cast vector to array pointer for address taking of components in opencl
REAL *zRotP = (REAL *)&zRot;
__constant REAL *colP = (__constant REAL *)&fractal->mandelbox.color.factor;
for (int dim = 0; dim < 3; dim++)
{
// handle each dimension x, y and z sequentially in pointer var dim
REAL *rotDim = (dim == 0) ? &zRotP[0] : ((dim == 1) ? &zRotP[1] : &zRotP[2]);
__constant REAL *colorFactor = (dim == 0) ? &colP[0] : ((dim == 1) ? &colP[1] : &colP[2]);
zRot = Matrix33MulFloat4(fractal->mandelbox.rot[0][dim], z);
if (*rotDim > fractal->mandelbox.foldingLimit)
{
*rotDim = fractal->mandelbox.foldingValue - *rotDim;
z = Matrix33MulFloat4(fractal->mandelbox.rotinv[0][dim], zRot);
aux->color += *colorFactor;
}
else
{
zRot = Matrix33MulFloat4(fractal->mandelbox.rot[1][dim], z);
if (*rotDim < -fractal->mandelbox.foldingLimit)
{
*rotDim = -fractal->mandelbox.foldingValue - *rotDim;
z = Matrix33MulFloat4(fractal->mandelbox.rotinv[1][dim], zRot);
aux->color += *colorFactor;
}
}
}
}
else
{
if (fabs(z.x) > fractal->mandelbox.foldingLimit)
{
z.x = sign(z.x) * fractal->mandelbox.foldingValue - z.x;
aux->color += fractal->mandelbox.color.factor.x;
}
if (fabs(z.y) > fractal->mandelbox.foldingLimit)
{
z.y = sign(z.y) * fractal->mandelbox.foldingValue - z.y;
aux->color += fractal->mandelbox.color.factor.y;
}
if (fabs(z.z) > fractal->mandelbox.foldingLimit)
{
z.z = sign(z.z) * fractal->mandelbox.foldingValue - z.z;
aux->color += fractal->mandelbox.color.factor.z;
}
}
REAL r2 = dot(z, z);
z += fractal->mandelbox.offset;
z = SphericalFold(z, r2, fractal, aux);
z -= fractal->mandelbox.offset;
if (fractal->mandelbox.mainRotationEnabled) z = Matrix33MulFloat4(fractal->mandelbox.mainRot, z);
z = z * fractal->mandelbox.scale;
aux->DE = aux->DE * fabs(fractal->mandelbox.scale) + 1.0f;
return z;
}
In C++ code you can do the same. You only need to create functions with unique names.
That is great news, as i have implemented some fractals laterly that will benefit by this method, as my current code is repeating the same calculation (i will try it out) and i did not want to add a lot to void sFractal::RecalculateFractalParams() for calculations that are only used by one formula
Ignore last thing i wrote as i was confusing myself
i can shorten the code a lot for some fractal if i use inline e.g mandalays where same function is written six times
but i could use void sFractal::RecalculateFractalParams() for this T>DIFS polyhedra // this block does not use z so could be a precalc REAL cospin = M_PI / (REAL)(Type); cospin = cos(cospin); REAL scospin = sqrt(0.75 - cospin * cospin); REAL4 nc = (REAL4)(-0.5, -cospin, scospin, 0.0); REAL4 pab = (REAL4)(0.0, 0.0, 1.0, 0.0); REAL4 pbc = normalize((REAL4)(scospin, 0.0, 0.5, 0.0)); REAL4 pca = normalize((REAL4)(0.0, scospin, cospin, 0.0));
currently i am repeating this calc for every point, with a constant input "Type" however the complete formula is fast so maybe not clutter up void sFractal::RecalculateFractalParams() by putting it there
c) add aux-> options to drop down menu
d) allow int to have negative value
e) editable parameter names
a) implement choose different DE function and method for boolean mode slots b) ability to write inline functions