00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #include "lux.h"
00025 #include "texture.h"
00026 #include "paramset.h"
00027 #include "error.h"
00028 #include "blender_texlib.h"
00029
00030 namespace lux {
00031
00032
00033 template <class T>
00034 class BlenderWoodTexture3D : public Texture<T> {
00035 public:
00036
00037
00038 ~BlenderWoodTexture3D() {
00039 delete mapping;
00040 }
00041
00042 BlenderWoodTexture3D(
00043 boost::shared_ptr<Texture<T> > c1,
00044 boost::shared_ptr<Texture<T> > c2,
00045 float noiseSize,
00046 short noiseType,
00047 float turbul,
00048 short sType,
00049 short noiseBasis2,
00050 short noiseBasis,
00051 float bright,
00052 float contrast,
00053 TextureMapping3D *map) : mapping(map) {
00054 tex.type = TEX_WOOD;
00055
00056 tex.noisesize = noiseSize;
00057 tex.noisetype = noiseType;
00058 tex.turbul = turbul;
00059 tex.stype = sType;
00060 tex.noisebasis = noiseBasis;
00061 tex.noisebasis2 = noiseBasis2;
00062 tex.bright = bright;
00063 tex.contrast = contrast;
00064 tex1 = c1;
00065 tex2 = c2;
00066 }
00067
00068 T Evaluate(const DifferentialGeometry &dg) const {
00069 Vector dpdx, dpdy;
00070 Point P = mapping->Map(dg, &dpdx, &dpdy);
00071
00072 blender::TexResult texres;
00073 int resultType = multitex(&tex, &P.x, &texres);
00074
00075 if(resultType & TEX_RGB)
00076 texres.tin = (0.35 * texres.tr + 0.45 * texres.tg
00077 + 0.2 * texres.tb);
00078 else
00079 texres.tr = texres.tg = texres.tb = texres.tin;
00080
00081 T t1 = tex1->Evaluate(dg), t2 = tex2->Evaluate(dg);
00082 return (1.f - texres.tin) * t1 + texres.tin * t2;
00083 }
00084
00085 static Texture<float> *CreateFloatTexture(const Transform &tex2world, const TextureParams &tp);
00086 static Texture<Spectrum> *CreateSpectrumTexture(const Transform &tex2world, const TextureParams &tp);
00087 private:
00088
00089
00090 TextureMapping3D *mapping;
00091 boost::shared_ptr<Texture<T> > tex1, tex2;
00092 blender::Tex tex;
00093 };
00094
00095 template <class T> Texture<float> *BlenderWoodTexture3D<T>::CreateFloatTexture(
00096 const Transform &tex2world,
00097 const TextureParams &tp) {
00098
00099 TextureMapping3D *map = new IdentityMapping3D(tex2world);
00100
00101 IdentityMapping3D *imap = (IdentityMapping3D*) map;
00102 imap->Apply3DTextureMappingOptions(tp);
00103
00104 boost::shared_ptr<Texture<float> > tex1 = tp.GetFloatTexture("tex1", 1.f);
00105 boost::shared_ptr<Texture<float> > tex2 = tp.GetFloatTexture("tex2", 0.f);
00106
00107
00108 short type = TEX_BAND;
00109 string stype = tp.FindString("type");
00110 if ((stype == "bands") || (stype == ""))
00111 type = TEX_BAND;
00112 else if (stype == "rings")
00113 type = TEX_RING;
00114 else if (stype == "bandnoise")
00115 type = TEX_BANDNOISE;
00116 else if (stype == "ringnoise")
00117 type = TEX_RINGNOISE;
00118 else {
00119 std::stringstream ss;
00120 ss << "Unknown noise type '" << stype << "'";
00121 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00122 }
00123
00124
00125 short ntype = TEX_NOISEPERL;
00126 string noiseType = tp.FindString("noisetype");
00127 if ((noiseType == "soft_noise") || (noiseType == ""))
00128 ntype = TEX_NOISESOFT;
00129 else if (noiseType == "hard_noise")
00130 ntype = TEX_NOISEPERL;
00131 else {
00132 std::stringstream ss;
00133 ss << "Unknown noise type '" << noiseType << "'";
00134 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00135 }
00136
00137
00138 short basis = TEX_BLENDER;
00139 string noiseBasis = tp.FindString("noisebasis");
00140 if ((noiseBasis == "blender_original") || (noiseBasis == ""))
00141 basis = TEX_BLENDER;
00142 else if (noiseBasis == "original_perlin")
00143 basis = TEX_STDPERLIN;
00144 else if (noiseBasis == "improved_perlin")
00145 basis = TEX_NEWPERLIN;
00146 else if (noiseBasis == "voronoi_f1")
00147 basis = TEX_VORONOI_F1;
00148 else if (noiseBasis == "voronoi_f2")
00149 basis = TEX_VORONOI_F2;
00150 else if (noiseBasis == "voronoi_f3")
00151 basis = TEX_VORONOI_F3;
00152 else if (noiseBasis == "voronoi_f4")
00153 basis = TEX_VORONOI_F4;
00154 else if (noiseBasis == "voronoi_f2f1")
00155 basis = TEX_VORONOI_F2F1;
00156 else if (noiseBasis == "voronoi_crackle")
00157 basis = TEX_VORONOI_CRACKLE;
00158 else if (noiseBasis == "cell_noise")
00159 basis = TEX_CELLNOISE;
00160 else {
00161 std::stringstream ss;
00162 ss << "Unknown noise basis '" << noiseBasis << "'";
00163 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00164 }
00165
00166
00167 short basis2 = TEX_SIN;
00168 string noiseBasis2 = tp.FindString("noisebasis2");
00169 if ((noiseBasis2 == "sin") || (noiseBasis2 == ""))
00170 basis2 = TEX_SIN;
00171 else if (noiseBasis2 == "saw")
00172 basis2 = TEX_SAW;
00173 else if (noiseBasis2 == "tri")
00174 basis2 = TEX_TRI;
00175 else {
00176 std::stringstream ss;
00177 ss << "Unknown noise basis2 '" << noiseBasis2 << "'";
00178 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00179 }
00180
00181 return new BlenderWoodTexture3D<float>(
00182 tex1,
00183 tex2,
00184 tp.FindFloat("noisesize", 0.250f),
00185 ntype,
00186 tp.FindFloat("turbulance", 5.0f),
00187 type,
00188 basis2,
00189 basis,
00190 tp.FindFloat("bright", 1.0f),
00191 tp.FindFloat("contrast", 1.0f),
00192 map);
00193 }
00194
00195 template <class T> Texture<Spectrum> *BlenderWoodTexture3D<T>::CreateSpectrumTexture(
00196 const Transform &tex2world,
00197 const TextureParams &tp) {
00198
00199 TextureMapping3D *map = new IdentityMapping3D(tex2world);
00200
00201 IdentityMapping3D *imap = (IdentityMapping3D*) map;
00202 imap->Apply3DTextureMappingOptions(tp);
00203
00204 boost::shared_ptr<Texture<Spectrum> > tex1 = tp.GetSpectrumTexture("tex1", 1.f);
00205 boost::shared_ptr<Texture<Spectrum> > tex2 = tp.GetSpectrumTexture("tex2", 0.f);
00206
00207
00208 short type = TEX_BAND;
00209 string stype = tp.FindString("type");
00210 if ((stype == "bands") || (stype == ""))
00211 type = TEX_BAND;
00212 else if (stype == "rings")
00213 type = TEX_RING;
00214 else if (stype == "bandnoise")
00215 type = TEX_BANDNOISE;
00216 else if (stype == "ringnoise")
00217 type = TEX_RINGNOISE;
00218 else {
00219 std::stringstream ss;
00220 ss << "Unknown noise type '" << stype << "'";
00221 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00222 }
00223
00224
00225 short ntype = TEX_NOISEPERL;
00226 string noiseType = tp.FindString("noisetype");
00227 if ((noiseType == "soft_noise") || (noiseType == ""))
00228 ntype = TEX_NOISESOFT;
00229 else if (noiseType == "hard_noise")
00230 ntype = TEX_NOISEPERL;
00231 else {
00232 std::stringstream ss;
00233 ss << "Unknown noise type '" << noiseType << "'";
00234 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00235 }
00236
00237
00238 short basis = TEX_BLENDER;
00239 string noiseBasis = tp.FindString("noisebasis");
00240 if ((noiseBasis == "blender_original") || (noiseBasis == ""))
00241 basis = TEX_BLENDER;
00242 else if (noiseBasis == "original_perlin")
00243 basis = TEX_STDPERLIN;
00244 else if (noiseBasis == "improved_perlin")
00245 basis = TEX_NEWPERLIN;
00246 else if (noiseBasis == "voronoi_f1")
00247 basis = TEX_VORONOI_F1;
00248 else if (noiseBasis == "voronoi_f2")
00249 basis = TEX_VORONOI_F2;
00250 else if (noiseBasis == "voronoi_f3")
00251 basis = TEX_VORONOI_F3;
00252 else if (noiseBasis == "voronoi_f4")
00253 basis = TEX_VORONOI_F4;
00254 else if (noiseBasis == "voronoi_f2f1")
00255 basis = TEX_VORONOI_F2F1;
00256 else if (noiseBasis == "voronoi_crackle")
00257 basis = TEX_VORONOI_CRACKLE;
00258 else if (noiseBasis == "cell_noise")
00259 basis = TEX_CELLNOISE;
00260 else {
00261 std::stringstream ss;
00262 ss << "Unknown noise basis '" << noiseBasis << "'";
00263 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00264 }
00265
00266
00267 short basis2 = TEX_SIN;
00268 string noiseBasis2 = tp.FindString("noisebasis2");
00269 if ((noiseBasis2 == "sin") || (noiseBasis2 == ""))
00270 basis2 = TEX_SIN;
00271 else if (noiseBasis2 == "saw")
00272 basis2 = TEX_SAW;
00273 else if (noiseBasis2 == "tri")
00274 basis2 = TEX_TRI;
00275 else {
00276 std::stringstream ss;
00277 ss << "Unknown noise basis2 '" << noiseBasis2 << "'";
00278 luxError(LUX_BADTOKEN, LUX_ERROR, ss.str().c_str());
00279 }
00280
00281 return new BlenderWoodTexture3D<Spectrum>(
00282 tex1,
00283 tex2,
00284 tp.FindFloat("noisesize", 0.250f),
00285 ntype,
00286 tp.FindFloat("turbulance", 5.0f),
00287 type,
00288 basis2,
00289 basis,
00290 tp.FindFloat("bright", 1.0f),
00291 tp.FindFloat("contrast", 1.0f),
00292 map);
00293 }
00294
00295 }