コード例 #1
0
ファイル: Photon.cs プロジェクト: acs3235/VTS
        /// <summary>
        /// Method that determines whether photon reflects or refracts across interface.  When this
        /// method is called photon is sitting on boundary of region and CurrentRegionIndex is Index
        /// of region photon had been in.
        /// </summary>
        public void CrossRegionOrReflect()
        {
            double cosTheta      = _tissue.GetAngleRelativeToBoundaryNormal(this);
            double nCurrent      = _tissue.Regions[CurrentRegionIndex].RegionOP.N;
            int    neighborIndex = _tissue.GetNeighborRegionIndex(this);
            double nNext         = _tissue.Regions[neighborIndex].RegionOP.N;

            double coscrit;

            if (nCurrent > nNext)
            {
                coscrit = Math.Sqrt(1.0 - (nNext / nCurrent) * (nNext / nCurrent));
            }
            else
            {
                coscrit = 0.0;
            }

            double probOfReflecting;
            double cosThetaSnell;

            // call Fresnel be default to have uZSnell set, used to be within else
            probOfReflecting = Optics.Fresnel(nCurrent, nNext, cosTheta, out cosThetaSnell);
            if (cosTheta <= coscrit)
            {
                probOfReflecting = 1.0;
            }
            //else
            //    probOfReflecting = Optics.Fresnel(nCurrent, nNext, cosTheta, out cosThetaSnell);

            /* Decide whether or not photon goes to next region */
            // perform first check so that rng not called on pseudo-collisions
            if ((probOfReflecting == 0.0) || (_rng.NextDouble() > probOfReflecting)) // transmitted
            {
                // if at border of system
                if (_tissue.OnDomainBoundary(this.DP.Position) && !_firstTimeEnteringDomain)
                {
                    DP.StateFlag = DP.StateFlag.Add(_tissue.GetPhotonDataPointStateOnExit(DP.Position));

                    // adjust CAW weight for portion of track prior to exit
                    if (Absorb == AbsorbContinuous)
                    {
                        AbsorbContinuous();
                    }

                    CurrentRegionIndex = neighborIndex;
                    //don't need to update these unless photon not dead upon exiting tissue
                    //DP.Direction.Ux *= nCurrent / nNext;
                    //DP.Direction.Uy *= nCurrent / nNext;
                    //DP.Direction.Uz = uZSnell;
                }
                else // not on domain boundary, at internal interface or first time enter tissue, pass to next
                {
                    CurrentRegionIndex = neighborIndex;
                    DP.Direction       = _tissue.GetRefractedDirection(DP.Position, DP.Direction,
                                                                       nCurrent, nNext, cosThetaSnell);
                    if (_firstTimeEnteringDomain)
                    {
                        _firstTimeEnteringDomain = false;
                    }
                }
            }
            else  // don't cross, reflect
            {
                DP.Direction = _tissue.GetReflectedDirection(DP.Position, DP.Direction);
                // check if specular reflection
                if (_firstTimeEnteringDomain)
                {
                    DP.StateFlag = DP.StateFlag.Add(PhotonStateType.PseudoSpecularTissueBoundary);
                }
            }
        }