00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "lux.h"
00024 #include "texture.h"
00025 #include "paramset.h"
00026 #include "error.h"
00027 #include "blender_texlib.h"
00028
00029 namespace lux {
00030
00031 template <class T>
00032 class BlenderVoronoiTexture3D : public Texture<T> {
00033 public:
00034
00035
00036 ~BlenderVoronoiTexture3D() {
00037 delete mapping;
00038 }
00039
00040 BlenderVoronoiTexture3D(
00041 boost::shared_ptr<Texture<T> > c1,
00042 boost::shared_ptr<Texture<T> > c2,
00043 short colType,
00044 short distMetric,
00045 float mExp,
00046 float ns_outscale,
00047 float noiseSize,
00048 float nabla,
00049 float w1,
00050 float w2,
00051 float w3,
00052 float w4,
00053 float bright,
00054 float contrast,
00055 TextureMapping3D *map) : mapping(map) {
00056 tex.type = TEX_VORONOI;
00057
00058 tex.vn_coltype = colType;
00059 tex.vn_distm = distMetric;
00060
00061 tex.vn_mexp = mExp;
00062 tex.ns_outscale = ns_outscale;
00063 tex.noisesize = noiseSize;
00064 tex.nabla = nabla;
00065
00066 tex.vn_w1 = w1;
00067 tex.vn_w2 = w2;
00068 tex.vn_w3 = w3;
00069 tex.vn_w4 = w4;
00070 tex.bright = bright;
00071 tex.contrast = contrast;
00072 tex.rfac = 1.0f;
00073 tex.gfac = 1.0f;
00074 tex.bfac = 1.0f;
00075
00076 tex1 = c1;
00077 tex2 = c2;
00078 }
00079
00080 T Evaluate(const DifferentialGeometry &dg) const {
00081 Vector dpdx, dpdy;
00082 Point P = mapping->Map(dg, &dpdx, &dpdy);
00083
00084 blender::TexResult texres;
00085 int resultType = multitex(&tex, &P.x, &texres);
00086
00087 if((resultType & TEX_RGB) && (!(resultType & TEX_INT)))
00088 texres.tin = (0.35 * texres.tr + 0.45 * texres.tg
00089 + 0.2 * texres.tb);
00090 else if((resultType & TEX_INT) && (!(resultType & TEX_RGB)))
00091 texres.tr = texres.tg = texres.tb = texres.tin;
00092
00093 T t1 = tex1->Evaluate(dg), t2 = tex2->Evaluate(dg);
00094 return (1.f - texres.tin) * t1 + texres.tin * t2;
00095 }
00096
00097 static Texture<float> *CreateFloatTexture(const Transform &tex2world, const TextureParams &tp);
00098 static Texture<Spectrum> *CreateSpectrumTexture(const Transform &tex2world, const TextureParams &tp);
00099 private:
00100
00101
00102 TextureMapping3D *mapping;
00103 boost::shared_ptr<Texture<T> > tex1, tex2;
00104 blender::Tex tex;
00105 };
00106
00107 template <class T> Texture<float> *BlenderVoronoiTexture3D<T>::CreateFloatTexture(
00108 const Transform &tex2world,
00109 const TextureParams &tp) {
00110
00111 TextureMapping3D *map = new IdentityMapping3D(tex2world);
00112
00113 IdentityMapping3D *imap = (IdentityMapping3D*) map;
00114 imap->Apply3DTextureMappingOptions(tp);
00115
00116 boost::shared_ptr<Texture<float> > tex1 = tp.GetFloatTexture("tex1", 1.f);
00117 boost::shared_ptr<Texture<float> > tex2 = tp.GetFloatTexture("tex2", 0.f);
00118
00119
00120 short distType = TEX_DISTANCE;
00121 string sDistType = tp.FindString("distmetric");
00122 if ((sDistType == "actual_distance") || (sDistType == ""))
00123 distType = TEX_DISTANCE;
00124 else if (sDistType == "distance_squared")
00125 distType = TEX_DISTANCE_SQUARED;
00126 else if (sDistType == "manhattan")
00127 distType = TEX_MANHATTAN;
00128 else if (sDistType == "chebychev")
00129 distType = TEX_CHEBYCHEV;
00130 else if (sDistType == "minkovsky_half")
00131 distType = TEX_MINKOVSKY_HALF;
00132 else if (sDistType == "minkovsky_four")
00133 distType = TEX_MINKOVSKY_FOUR;
00134 else if (sDistType == "minkovsky")
00135 distType = TEX_MINKOVSKY;
00136 else {
00137 std::stringstream ss;
00138 ss << "Unknown distance metric '" << sDistType << "'";
00139 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00140 }
00141
00142 return new BlenderVoronoiTexture3D<float>(
00143 tex1,
00144 tex2,
00145 tp.FindInt("coltype", 0),
00146 distType,
00147 tp.FindFloat("minkovsky_exp", 2.5f),
00148 tp.FindFloat("outscale", 1.0f),
00149 tp.FindFloat("noisesize", 0.25f),
00150 tp.FindFloat("nabla", 0.025f),
00151 tp.FindFloat("w1", 1.0f),
00152 tp.FindFloat("w2", 0.0f),
00153 tp.FindFloat("w3", 0.0f),
00154 tp.FindFloat("w4", 0.0f),
00155 tp.FindFloat("bright", 1.0f),
00156 tp.FindFloat("contrast", 1.0f),
00157 map);
00158 }
00159
00160 template <class T> Texture<Spectrum> *BlenderVoronoiTexture3D<T>::CreateSpectrumTexture(
00161 const Transform &tex2world,
00162 const TextureParams &tp) {
00163
00164 TextureMapping3D *map = new IdentityMapping3D(tex2world);
00165
00166 IdentityMapping3D *imap = (IdentityMapping3D*) map;
00167 imap->Apply3DTextureMappingOptions(tp);
00168
00169 boost::shared_ptr<Texture<Spectrum> > tex1 = tp.GetSpectrumTexture("tex1", 1.f);
00170 boost::shared_ptr<Texture<Spectrum> > tex2 = tp.GetSpectrumTexture("tex2", 0.f);
00171
00172
00173 short distType = TEX_DISTANCE;
00174 string sDistType = tp.FindString("distmetric");
00175 if ((sDistType == "actual_distance") || (sDistType == ""))
00176 distType = TEX_DISTANCE;
00177 else if (sDistType == "distance_squared")
00178 distType = TEX_DISTANCE_SQUARED;
00179 else if (sDistType == "manhattan")
00180 distType = TEX_MANHATTAN;
00181 else if (sDistType == "chebychev")
00182 distType = TEX_CHEBYCHEV;
00183 else if (sDistType == "minkovsky_half")
00184 distType = TEX_MINKOVSKY_HALF;
00185 else if (sDistType == "minkovsky_four")
00186 distType = TEX_MINKOVSKY_FOUR;
00187 else if (sDistType == "minkovsky")
00188 distType = TEX_MINKOVSKY;
00189 else {
00190 std::stringstream ss;
00191 ss << "Unknown distance metric '" << sDistType << "'";
00192 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00193 }
00194
00195 return new BlenderVoronoiTexture3D<Spectrum>(
00196 tex1,
00197 tex2,
00198 tp.FindInt("coltype", 0),
00199 distType,
00200 tp.FindFloat("minkovsky_exp", 2.5f),
00201 tp.FindFloat("outscale", 1.0f),
00202 tp.FindFloat("noisesize", 0.25f),
00203 tp.FindFloat("nabla", 0.025f),
00204 tp.FindFloat("w1", 1.0f),
00205 tp.FindFloat("w2", 0.0f),
00206 tp.FindFloat("w3", 0.0f),
00207 tp.FindFloat("w4", 0.0f),
00208 tp.FindFloat("bright", 1.0f),
00209 tp.FindFloat("contrast", 1.0f),
00210 map);
00211 }
00212
00213 }