protected override RgbSpectrumInfo Evaluate(ref HitPointInfo HitPoint, ref Vector localLightDir, ref Vector localEyeDir, out BsdfEvent _event, out float directPdfW, out float reversePdfW) { _event = this.Type.TypeToEvent(); directPdfW = 0f; reversePdfW = 0f; return RgbSpectrumInfo.Black; }
protected override RgbSpectrumInfo Evaluate(ref HitPointInfo HitPoint, ref Vector localLightDir, ref Vector localEyeDir, out BsdfEvent _event, out float directPdfW, out float reversePdfW) { _event = BsdfEvent.Diffuse | BsdfEvent.Reflect; directPdfW = Math.Abs((HitPoint.FromLight ? localEyeDir.z : localLightDir.z) * MathLab.INVPI); reversePdfW = Math.Abs((HitPoint.FromLight ? localLightDir.z : localEyeDir.z) * MathLab.INVPI); var kd = TexData.Diffuse; return (kd * MathLab.INVPI); }
public override void Sample_f(ShadePointInfo pt, float u0, float u1, float u2, out Vector vector, out float radiancePdf, out float pdf1, out BsdfEvent @event) { float c = 1f - Vector.Dot(ref pt.IncomingDirection, ref pt.ShadingNormal); float Re = R0 + (1f - R0) * c * c * c * c * c; float P = .25f + .5f * Re; if ((u2 < P && reflectionSpecularBounce)) {//onlySpecular || vector = MetalBrdf.GlossyReflection(ref pt.IncomingDirection, exponent, ref pt.ShadingNormal, u0, u1); pdf1 = P / Re; @event = BsdfEvent.Specular; radiancePdf = Re; } else { Vector dir = MC.CosineSampleHemisphere(u0, u1); pdf1 = dir.z * MathLab.INVPI; /* Vector v1, v2; * dir = Vector.CoordinateSystem(ref shadeN, out v1, out v2); dir = new Vector( v1.x * dir.x + v2.x * dir.y + shadeN.x * dir.z, v1.y * dir.x + v2.y * dir.y + shadeN.y * dir.z, v1.z * dir.x + v2.z * dir.y + shadeN.z * dir.z);*/ ONB fm = new ONB(ref pt.ShadingNormal); var wi = fm.ToWorld(ref dir);//pt.Frame float dp = Vector.Dot(ref pt.ShadingNormal, ref wi); // Using 0.0001 instead of 0.0 to cut down fireflies if (dp <= 0.0001f) { pdf1 = 0f; } pdf1 /= dp; float iRe = 1f - Re; pdf1 *= (1f - P) / iRe; @event = BsdfEvent.Glossy | BsdfEvent.Diffuse; vector = wi; radiancePdf = iRe; } }
protected override RgbSpectrum Sample(ref HitPointInfo HitPoint, ref Vector localFixedDir, out Vector localSampledDir, float u0, float u1, out float pdfW, out float absCosDir, out BsdfEvent _event) { _event = this.Type.TypeToEvent(); localSampledDir = new Vector(-localFixedDir.x, -localFixedDir.y, localFixedDir.z); pdfW = 1f; absCosDir = Math.Abs(localSampledDir.z); var kr = (RgbSpectrum)TexData.Specular; // The absCosSampledDir is used to compensate the other one used inside the integrator return kr / absCosDir; }
public override void Sample_f(ShadePointInfo point, float u0, float u1, float u2, out Vector wi, out float radiance, out float pdf, out BsdfEvent bsdfEvent) { Vector dir = MC.CosineSampleHemisphere(u0, u1); pdf = dir.z * MathLab.INVPI; bsdfEvent = BsdfEvent.Diffuse; wi = point.Frame.ToWorld(ref dir); float dp = (Normal.Dot(ref point.GeoNormal, ref wi)); if (dp <= 0.01f) { pdf = 0f; bsdfEvent = BsdfEvent.Absorb; radiance = 0f; } else { pdf /= dp; radiance = MathLab.INVPI; } }
protected override RgbSpectrum Sample(ref HitPointInfo HitPoint, ref Vector localFixedDir, out Vector localSampledDir, float u0, float u1, out float pdfW, out float absCosDir, out BsdfEvent _event) { absCosDir = 0f; _event = BsdfEvent.Diffuse | BsdfEvent.Reflect; pdfW = 0f; localSampledDir = new Vector(); if (Math.Abs(localFixedDir.z) < MathLab.COS_EPSILON_STATIC) return RgbSpectrum.ZeroSpectrum(); localSampledDir = Sgn(localFixedDir.z) * MC.CosineSampleHemisphere(u0, u1, out pdfW); absCosDir = Math.Abs(localSampledDir.z); if (absCosDir < MathLab.COS_EPSILON_STATIC) return RgbSpectrum.ZeroSpectrum(); var kd = (RgbSpectrum)(TexData.Diffuse); kd.Mul(MathLab.INVPI); return (kd); }
public override void InitPath(IPathProcessor buffer) { base.InitPath(buffer); this.scene = pathIntegrator.Scene; this.Radiance = new RgbSpectrum(0f); this.Throughput = new RgbSpectrum(1f); this.PathState = PathTracerPathState.EyeVertex; if (this.secRays == null) { this.secRays = new ShadowRayInfo[scene.ShadowRaysPerSample+10]; continueRays = new ShadowRayInfo[scene.ShadowRaysPerSample+10]; } contCount = 0; this.Sample = pathIntegrator.Sampler.GetSample(this.Sample); pathIntegrator.Scene.Camera.GetRay(Sample.imageX, Sample.imageY, out this.PathRay); this.RayIndex = -1; this.tracedShadowRayCount = 0; this.depth = 0; this.bsdfEvent = BsdfEvent.Specular; this.prevEvent = BsdfEvent.None; shadowRayEvent = BsdfEvent.None; }
protected override RgbSpectrum Sample(ref HitPointInfo HitPoint, ref Vector localFixedDir, out Vector localSampledDir, float u0, float u1, out float pdfW, out float absCosDir, out BsdfEvent _event) { _event = this.Type.TypeToEvent(); localSampledDir = new Vector(-localFixedDir.x, -localFixedDir.y, localFixedDir.z); pdfW = 1f; absCosDir = Math.Abs(localSampledDir.z); var kr = (RgbSpectrum)TexData.Specular; float e = 1f / (Math.Max(TexData.Exponent, 0f) + 1f); localSampledDir = GlossyReflection(ref localFixedDir, e, u0, u1); if (localSampledDir.z * localFixedDir.z > 0f) { _event = BsdfEvent.Specular | BsdfEvent.Reflect; pdfW = 1f; absCosDir = Math.Abs(localSampledDir.z); // The absCosSampledDir is used to compensate the other one used inside the integrator return kr / (absCosDir); } else return RgbSpectrum.ZeroSpectrum(); }
public RgbSpectrum Sample_f(ref Vector wo, out Vector wi, ref Normal N, ref Normal shadeN, ref RgbSpectrum in_fs, float u0, float u1, float u2, ref SurfaceTextureData surfaceData, out float pdf, out BsdfEvent bsdfEvent) { throw new NotImplementedException(); }
public RgbSpectrum Sample(out Vector dir, float u0, float u1, float u2, out float pdfW, out float absCosDir, out BsdfEvent _event) { Vector localFixedDir = Frame.ToLocal(ref HitPoint.FromDirection); Vector localSampledDir; dir = new Vector(); var result = this.Sample(ref HitPoint, ref localFixedDir, out localSampledDir, u0, u1, out pdfW, out absCosDir, out _event); if (result.IsBlack()) return result; dir = Frame.ToWorld(ref localSampledDir); #if VERBOSE RayDen.Library.Core.Components.Assert.IsNotNaN(result.c1); RayDen.Library.Core.Components.Assert.IsNotNaN(result.c2); RayDen.Library.Core.Components.Assert.IsNotNaN(result.c3); #endif // Adjoint BSDF if (HitPoint.FromLight) { float absDotFixedDirNS = Math.Abs(localFixedDir.z); float absDotSampledDirNS = Math.Abs(localSampledDir.z); float absDotFixedDirNG = Vector.AbsDot(ref HitPoint.FromDirection, ref HitPoint.GeoNormal); float absDotSampledDirNG = Vector.AbsDot(ref dir, ref HitPoint.GeoNormal); return result * ((absDotFixedDirNS * absDotSampledDirNG) / (absDotSampledDirNS * absDotFixedDirNG)); } else return result; }
public override void InitPath(IPathProcessor buffer) { base.InitPath(buffer); this.scene = pathIntegrator.Scene; if (Vertices == null) { Vertices = new PathVertex[scene.MaxPathDepth * 3]; Xvertices = new PathVertex[scene.MaxPathDepth * 3]; } this.pathDensity = 1.0f; this.Radiance = new RgbSpectrum(0f); this.Throughput = new RgbSpectrum(1f); this.PathState = PathTracerPathState.EyeVertex; if (!mutate) { this.Sample = pathIntegrator.Sampler.GetSample(this.Sample); pathIntegrator.Scene.Camera.GetRay(Sample.imageX, Sample.imageY, out this.PathRay); pathStart = PathRay.Org; XRadiance = new RgbSpectrum(); xPathDensity = 1.0f; } else { PathRay.Org = pathStart; PathRay.Dir = -Vertices[0].Wo; this.BackupPath(); this.MutatePath(); mutationCount++; if (mutationCount > MaxMutations) { this.mutate = false; this.mutationCount = 0; this.InitPath(buffer); } } this.RayIndex = -1; this.depth = 0; this.bsdfEvent = BsdfEvent.Specular; this.prevEvent = BsdfEvent.None; shadowRayEvent = BsdfEvent.None; }
public override void Sample_f(ShadePointInfo pt, float u0, float u1, float u2, out Vector Wi, out float radiancePdf, out float pdf, out BsdfEvent @event) { Vector rayDir = -pt.IncomingDirection; var N = pt.GeoNormal; var shadeN = pt.ShadingNormal; var wi = new Vector(); var N1 = N.ToVec(); var reflDir = rayDir - (2f * (Normal.Dot(ref N, ref rayDir))) * N1; // Ray from outside going in ? bool into = ((Normal.Dot(ref N, ref shadeN)) > 0); float nc = n0; float nt = n1; float nnt = into ? (nc / nt) : (nt / nc); float ddn = (rayDir & shadeN.ToVec()); float cos2t = 1f - nnt * nnt * (1f - ddn * ddn); radiancePdf = 0f; // Total internal reflection if (cos2t < 0f) { wi = reflDir; pdf = 1f; @event = BsdfEvent.Reflect | BsdfEvent.Specular; radiancePdf = 1f; Wi = wi; return; } float kk = (into ? 1f : -1f) * (ddn * nnt + MathLab.Sqrt((cos2t))); Vector nkk = kk * N1; Vector transDir = (nnt * rayDir - nkk).Normalize(); float c = 1f - (into ? -ddn : (transDir & N1)); float Re = R0 + (1f - R0) * c * c * c * c * c; float Tr = 1f - Re; float P = .25f + .5f * Re; if (Tr.NearEqual(0f)) { if (Re.NearEqual(0f)) { pdf = 0f; @event = BsdfEvent.Absorb; } else { (wi) = reflDir; pdf = 1f; radiancePdf = 1f; @event = BsdfEvent.Reflect | BsdfEvent.Specular; Wi = wi; return; } } else if (Re.NearEqual(0f)) { (wi) = transDir; pdf = 1f; @event = BsdfEvent.Transmit | BsdfEvent.Specular; radiancePdf = 1.0f; } else if (u0 < P) { (wi) = reflDir; pdf = P / Re; radiancePdf = 1f; @event = BsdfEvent.Reflect | BsdfEvent.Specular; } else { (wi) = transDir; pdf = (1f - P) / Tr; @event = BsdfEvent.Transmit | BsdfEvent.Specular; radiancePdf = 1.0f; } Wi = wi; }
protected override RgbSpectrum Sample(ref HitPointInfo HitPoint, ref Vector localFixedDir, out Vector localSampledDir, float u0, float u1, out float pdfW, out float absCosDir, out BsdfEvent _event) { var kr = (RgbSpectrum)TexData.Gloss + 0.5f; var kt = (RgbSpectrum)(TexData.Transmittance??TexData.Diffuse) + 0.5f; bool isKtBlack = kt.IsBlack(); bool isKrBlack = kr.IsBlack(); _event = BsdfEvent.None; pdfW = 0f; absCosDir = 0f; localSampledDir = new Vector(); if (isKtBlack && isKrBlack) return RgbSpectrum.ZeroSpectrum(); bool entering = (CosTheta(ref localFixedDir) > 0f); float nc = TexData.PreviousMedium.IoR; float nt = TexData.Medium.IoR; float ntc = nt / nc; float eta = entering ? (nc / nt) : ntc; float costheta = CosTheta(ref localFixedDir); // Decide to transmit or reflect float threshold = isKrBlack ? 1f : (isKtBlack ? 0f : .5f); RgbSpectrum result; if (TexData.Event < threshold) { // Transmit // Compute transmitted ray direction float sini2 = SinTheta2(ref localFixedDir); float eta2 = eta * eta; float sint2 = eta2 * sini2; // Handle total internal reflection for transmission if (sint2 >= 1f) return RgbSpectrum.ZeroSpectrum(); float cost = MathLab.Sqrt(Math.Max(0f, 1f - sint2)) * (entering ? -1f : 1f); localSampledDir = new Vector(-eta * localFixedDir.x, -eta * localFixedDir.y, cost); absCosDir = Math.Abs(CosTheta(ref localSampledDir)); _event = BsdfEvent.Specular | BsdfEvent.Transmit; pdfW = threshold; if (!HitPoint.FromLight) result = (RgbSpectrum.UnitSpectrum() - FresnelCauchy_Evaluate(ntc, cost)) * eta2; else result = (RgbSpectrum.UnitSpectrum() - FresnelCauchy_Evaluate(ntc, costheta)); result *= kt; } else { // Reflect localSampledDir = new Vector(-localFixedDir.x, -localFixedDir.y, localFixedDir.z); absCosDir = Math.Abs(CosTheta(ref localSampledDir)); _event = BsdfEvent.Specular | BsdfEvent.Reflect; pdfW = 1f - threshold; result = kr * FresnelCauchy_Evaluate(ntc, costheta); } // The absCosSampledDir is used to compensate the other one used inside the integrator return result / (absCosDir); }
public abstract void Sample_f(ShadePointInfo point, float u0, float u1, float u2, out Vector vector, out float radiancePdf, out float pdf1, out BsdfEvent @event);
public static bool Has(this BsdfEvent val, BsdfEvent f) { //return val.HasFlag(f); return ((byte)val & (byte)f).Equals((byte)f); }
public override bool Match(bool isLight, bool isVolume, BsdfEvent hitEvent) { return isLight; }
//luxrays::Spectrum GetEmittedRadiance(float *directPdfA = NULL, float *emissionPdfW = NULL) const ; public RgbSpectrumInfo Evaluate(ref Vector generatedDir, out BsdfEvent _event, out float directPdfW, out float reversePdfW) { _event = this.Type.TypeToEvent(); directPdfW = 0f; reversePdfW = 0f; Vector eyeDir = HitPoint.FromLight ? generatedDir : HitPoint.FromDirection; Vector lightDir = HitPoint.FromLight ? HitPoint.FromDirection : generatedDir; float dotLightDirNG = Vector.Dot(ref lightDir, ref HitPoint.GeoNormal); float absDotLightDirNG = Math.Abs(dotLightDirNG); float dotEyeDirNG = Vector.Dot(ref eyeDir, ref HitPoint.GeoNormal); float absDotEyeDirNG = Math.Abs(dotEyeDirNG); if ((absDotLightDirNG < MathLab.COS_EPSILON_STATIC) || (absDotEyeDirNG < MathLab.COS_EPSILON_STATIC)) return RgbSpectrumInfo.Black; float sideTest = dotEyeDirNG * dotLightDirNG; if (((sideTest > 0f) && !(this.Type.Has(BrdfType.Reflection))) ||(((sideTest < 0f) && !(this.Type.Has(BrdfType.Refractive))))) return RgbSpectrumInfo.Black; Vector localLightDir = Frame.ToLocal(ref lightDir); Vector localEyeDir = Frame.ToLocal(ref eyeDir); RgbSpectrumInfo result = this.Evaluate(ref HitPoint, ref localLightDir, ref localEyeDir, out _event, out directPdfW, out reversePdfW); #if VERBOSE RayDen.Library.Core.Components.Assert.IsNotNaN(result.c1); RayDen.Library.Core.Components.Assert.IsNotNaN(result.c2); RayDen.Library.Core.Components.Assert.IsNotNaN(result.c3); #endif // Adjoint BSDF if (HitPoint.FromLight) { float absDotLightDirNS = Vector.AbsDot(ref lightDir, ref HitPoint.ShadingNormal); float absDotEyeDirNS = Vector.AbsDot(ref eyeDir, ref HitPoint.ShadingNormal); return result * ((absDotLightDirNS * absDotEyeDirNG) / (absDotEyeDirNS * absDotLightDirNG)); } else return result; }
public virtual bool Match(bool isLight, bool isVolume, BsdfEvent hitEvent) { return false; }
protected abstract RgbSpectrum Sample(ref HitPointInfo HitPoint, ref Vector localFixedDir, out Vector localSampledDir, float u0, float u1, out float pdfW, out float absCosDir, out BsdfEvent _event);
public RgbSpectrum Sample_f(ref Vector lwo, out Vector wi, ref Normal N, ref Normal shadeN, ref RgbSpectrum in_fs, float u0, float u1, float u2, ref SurfaceTextureData surfaceData, out float pdf, out BsdfEvent bsdfEvent) { this.CreateFrame(ref N); var wo = this.WorldToLocal(ref lwo); var res = new RgbSpectrum(); pdf = 0f; bsdfEvent = BsdfEvent.None; wi = new Vector(); ElementaryBrdf brdf; if (this.brdfs.Length == 1) { brdf = this.brdfs[0]; } else brdf = Sample(u2); if (brdf != null) { BsdfSampleData result; brdf.Sample_f(ref wo, ref N, ref shadeN, ref surfaceData, u0, u1, u2, out result); res = result.F; pdf = result.Pdf ; //*(1f / brdfs.Length); wi = LocalToWorld(ref result.Wi); bsdfEvent = brdf.Type.TypeToEvent(); } return res; }
protected abstract RgbSpectrumInfo Evaluate(ref HitPointInfo HitPoint, ref Vector localLightDir, ref Vector localEyeDir, out BsdfEvent _event, out float directPdfW, out float reversePdfW);