예제 #1
0
        public double GetDoseAtVolumeForUncertainties(curve DVH, double Volume, VolumePresentation VolPres, DoseValuePresentation RequestedDosePresentation)
        {
            double dose;

            if (DVH.VolumePresentation == VolumePresentation.AbsoluteCm3 && VolPres == VolumePresentation.Relative)
            {
                Volume = Volume * DVH.AbsoluteStructureVolume / 100.0;
            }

            if (DVH.VolumePresentation == VolumePresentation.Relative && VolPres == VolumePresentation.AbsoluteCm3)
            {
                Volume = Volume / DVH.AbsoluteStructureVolume * 100.0;
            }

            int ind1 = DVH.CurveData.Select(x => x.Volume).Count() - DVH.CurveData.Where(x => x.Volume < Volume).Select(x => x.Volume).Count() - 1;
            int ind2 = DVH.CurveData.Select(x => x.Volume).Count() - DVH.CurveData.Where(x => x.Volume < Volume).Select(x => x.Volume).Count();

            DVHPoint DVP1 = DVH.CurveData.ElementAt(ind1);
            DVHPoint DVP2 = DVH.CurveData.ElementAt(ind2);

            dose = Interpolate(DVP1.Volume, DVP2.Volume, DVP1.DoseValue.Dose, DVP2.DoseValue.Dose, Volume);

            if (DVH.DoseValuePresentation == DoseValuePresentation.Absolute && RequestedDosePresentation == DoseValuePresentation.Relative)
            {
                dose = dose / DVH.PrescribedDose * 100.0;
            }

            if (DVH.DoseValuePresentation == DoseValuePresentation.Relative && RequestedDosePresentation == DoseValuePresentation.Absolute)
            {
                dose = dose * DVH.PrescribedDose / 100.0;
            }

            return(dose);
        }
예제 #2
0
        /// <summary>
        /// Converts cumulative to differntial
        /// </summary>
        /// <param name="dvh">the dvh curve</param>
        /// <returns>the differential dvh</returns>
        public static DVHPoint[] Differential(this DVHPoint[] dvh)
        {
            var maxDose    = dvh.MaxDose();
            var volumeUnit = dvh.First().VolumeUnit;
            var minDose    = dvh.MinDose();

            List <DVHPoint> differential = new List <DVHPoint>();

            for (int i = 0; i < dvh.Length - 1; i++)
            {
                var pt1  = dvh[i];
                var pt2  = dvh[i + 1];
                var vol  = pt1.Volume - pt2.Volume;
                var dose = pt2.DoseValue.Dose - pt1.DoseValue.Dose;
                var ddvh = vol / dose;
                differential.Add(new DVHPoint(pt1.DoseValue, ddvh, volumeUnit));
            }
            //Normalize
            var max = differential.Max(d => d.Volume);

            for (int i = 0; i < differential.Count; i++)
            {
                var dv = differential[i];
                differential[i] = new DVHPoint(dv.DoseValue, dv.Volume / max, dv.VolumeUnit);
            }

            return(differential.ToArray());
        }
예제 #3
0
파일: DHV.cs 프로젝트: spw08536/eclipse
        private void exportDVH(PlanSetup plan, Structure target, string fileName)
        {
            // extract DVH data
            DVHData dvhData = plan.GetDVHCumulativeData(target,
                                                        DoseValuePresentation.Relative,
                                                        VolumePresentation.AbsoluteCm3, 0.1);

            if (dvhData == null)
            {
                throw new ApplicationException("No DVH data for target '" + target.Id + "'.");
            }

            // export DVH data as a CSV file
            using (System.IO.StreamWriter sw =
                       new System.IO.StreamWriter(fileName, false, Encoding.ASCII))
            {
                // write the header, assume the first dvh point represents the others
                DVHPoint rep = dvhData.CurveData[0];
                sw.WriteLine(
                    string.Format("Relative dose [{0}],Structure volume [{1}],",
                                  rep.DoseValue.UnitAsString, rep.VolumeUnit)
                    );
                // write each row of dose / volume data
                foreach (DVHPoint pt in dvhData.CurveData)
                {
                    sw.WriteLine(string.Format("{0:0.0},{1:0.00000}",
                                               pt.DoseValue.Dose, pt.Volume));
                }
            }
        }
예제 #4
0
 /// <summary>
 ///     If appropriate, converts the DVH curve into relative dose points instead of absolute dose
 /// </summary>
 /// <param name="dvh">the input DVH</param>
 /// <param name="scalingPoint">the dose value which represents 100%, all doses will be scaled in reference to this</param>
 /// <returns>the dvh with relative dose points</returns>
 public static DVHPoint[] ConvertToRelativeDose(this DVHPoint[] dvh, DoseValue scalingPoint)
 {
     if (dvh.Any() && dvh.First().DoseValue.Unit == DoseValue.DoseUnit.Percent)
     {
         return(dvh); //Already in relative format
     }
     for (var i = 0; i < dvh.Length; i++)
     {
         var dv = new DoseValue(dvh[i].DoseValue.Divide(scalingPoint).Dose * 100, DoseValue.DoseUnit.Percent);
         dvh[i] = new DVHPoint(dv, dvh[i].Volume, dvh[i].VolumeUnit);
     }
     return(dvh);
 }
예제 #5
0
        public void SerializeDeserializeDVHPoint()
        {
            var doseValue = new DoseValue(25, DoseValue.DoseUnit.Gy);
            var dp        = new DVHPoint(doseValue, 30, "cc");

            var serialized = FacadeSerializer.Serialize(dp);

            var deserialized = FacadeSerializer.Deserialize <DVHPoint>(serialized);

            Assert.AreEqual(deserialized.DoseValue, doseValue);
            Assert.AreEqual(deserialized.Volume, dp.Volume);
            Assert.AreEqual(deserialized.VolumeUnit, dp.VolumeUnit);
        }
예제 #6
0
        /// <summary>
        /// If appropriate, converts the DVH curve into relative volume points instead of absolute volume
        /// </summary>
        /// <param name="dvh">the input DVH</param>
        /// <returns>the dvh with relative volume points</returns>
        public static DVHPoint[] ConvertToRelativeVolume(this DVHPoint[] dvh)
        {
            var maxVol = dvh.Max(d => d.Volume);

            if (dvh.Any() && dvh.First().VolumeUnit != "%")
            {
                for (int i = 0; i < dvh.Length; i++)
                {
                    dvh[i] = new DVHPoint(dvh[i].DoseValue, 100 * dvh[i].Volume / maxVol, "%");
                }
            }
            return(dvh);
        }
예제 #7
0
        public void MeanDoseTest()
        {
            var dvh = new DVHPoint[]
            {
                new DVHPoint(new DoseValue(0, cGy), 0, "cc"),
                new DVHPoint(new DoseValue(50, cGy), 0, "cc"),
                new DVHPoint(new DoseValue(100, cGy), 0, "cc")
            };

            var actual   = dvh.MeanDose();
            var expected = new DoseValue(50, cGy);

            Assert.AreEqual(expected.Dose, actual.Dose, 0.0001);
        }
예제 #8
0
        public void ConvertToRelativeVolumeTest()
        {
            var dvh = new DVHPoint[]
            {
                new DVHPoint(new DoseValue(0, cGy), 0, "cc"),
                new DVHPoint(new DoseValue(100, cGy), 100, "cc"),
                new DVHPoint(new DoseValue(200, cGy), 200, "cc")
            };

            var relative = dvh.ConvertToRelativeVolume();

            Assert.AreEqual(relative[0].Volume, 0, 0.0001);
            Assert.AreEqual(relative[1].Volume, 50, 0.0001);
            Assert.AreEqual(relative[2].Volume, 100, 0.0001);
        }
예제 #9
0
        public override object ReadJson(JsonReader reader, Type objectType, object existingValue,
                                        JsonSerializer serializer)
        {
            // Load the JSON for the Result into a JObject
            var jo = JObject.Load(reader);

            // Read the properties which will be used as constructor parameters
            var jValue = (JObject)jo[nameof(DVHPoint.DoseValue)];
            var value  = serializer.Deserialize <DoseValue>(jValue.CreateReader());
            var vol    = (double)jo[nameof(DVHPoint.Volume)];
            var unit   = (string)jo[nameof(DVHPoint.VolumeUnit)];

            // Construct the Result object using the non-default constructor
            var dp = new DVHPoint(value, vol, unit);

            // Return the result
            return(dp);
        }
예제 #10
0
        /// <summary>
        /// Merges DVHData from multiple structures into one DVH by summing the volumes at each dose value
        /// </summary>
        /// <param name="dvhs"></param>
        /// <returns></returns>
        public static DVHPoint[] MergeDVHs(this IEnumerable <DVHData> dvhs)
        {
            var maxLength = dvhs.Max(d => d.CurveData.Length);
            var maxDVH    = dvhs.First(d => d.CurveData.Length == maxLength);
            var mergedDVH = maxDVH.CurveData.Select(d => new DVHPoint(d.DoseValue, 0, d.VolumeUnit)).ToArray();
            var volUnit   = dvhs.First().CurveData.First().VolumeUnit;

            if (volUnit == "%")
            {
                throw new ArgumentException("Cannot merge relative DVHs. Must be in absolute volume format");
            }

            foreach (var dvh in dvhs)
            {
                for (int i = 0; i < dvh.CurveData.Length; i++)
                {
                    var current = dvh.CurveData[i];
                    mergedDVH[i] = new DVHPoint(current.DoseValue, current.Volume + mergedDVH[i].Volume, current.VolumeUnit);
                }
            }

            return(mergedDVH);
        }
예제 #11
0
        /// <summary>
        ///     Merges DVHData from multiple structures into one DVH by summing the volumes at each dose value
        /// </summary>
        /// <param name="dvhs">the multiple dvh curves to merge</param>
        /// <returns>the combined dvh from multiple structures</returns>
        public static DVHPoint[] MergeDVHs(this IEnumerable <DVHPoint[]> dvhs)
        {
            //The merged DVH must be the same length as the maximum length DVH input
            var maxLength = dvhs.Max(d => d.Length);
            var maxDVH    = dvhs.First(d => d.Length == maxLength);
            var mergedDVH = maxDVH.Select(d => new DVHPoint(d.DoseValue, 0, d.VolumeUnit)).ToArray();

            //Lets check units before we continue
            var volUnit  = dvhs.First().First().VolumeUnit;
            var doseUnit = dvhs.First().First().DoseValue.Unit;

            if (dvhs.Any(d => d.First().DoseValue.Unit != doseUnit))
            {
                throw new ArgumentException("Cannot merge relative DVHs. All DVHs must have the same dose units");
            }
            if (dvhs.Any(d => d.First().VolumeUnit != volUnit))
            {
                throw new ArgumentException("Cannot merge relative DVHs. All DVHs must have the same volume units");
            }
            if (volUnit == MagicStrings.VolumeUnits.PERCENT)
            {
                throw new ArgumentException("Cannot merge relative DVHs. Must be in absolute volume format");
            }

            //Everything looks good, let's do it
            foreach (var dvh in dvhs)
            {
                for (var i = 0; i < dvh.Length; i++)
                {
                    var current = dvh[i];
                    mergedDVH[i] = new DVHPoint(current.DoseValue, current.Volume + mergedDVH[i].Volume,
                                                current.VolumeUnit);
                }
            }
            return(mergedDVH);
        }
예제 #12
0
 public static DataPoint CreateDataPoint(DVHPoint dvhPoint)
 {
     return(new DataPoint(dvhPoint.DoseValue.Dose, dvhPoint.Volume));
 }
예제 #13
0
 private DataPoint CreateDataPoint(DVHPoint p)
 {
     return(new DataPoint(p.DoseValue.Dose, p.Volume));
 }
예제 #14
0
        public void LoadDVH(Structure structure, PlanSetup plan, DoseValuePresentation dosePresentation, VolumePresentation volPresentation, bool useRapPlanEstim = false)
        {
            BinSize = Convert.ToDouble(Myconfig.GetAppKey("DVHBinSize"));
            DVHData      apiDVH    = null;
            EstimatedDVH upEstDVH  = null;
            EstimatedDVH lowEstDVH = null;

            if (volPresentation == VolumePresentation.AbsoluteCm3)
            {
                VolumeUnit = MyDVHData.VolumeUnits.cc;
            }
            else if (volPresentation == VolumePresentation.Relative)
            {
                VolumeUnit = MyDVHData.VolumeUnits.Percent;
            }
            else
            {
                VolumeUnit = MyDVHData.VolumeUnits.Unknown;
            }

            if (useRapPlanEstim)
            {
                upEstDVH  = plan.DVHEstimates.FirstOrDefault(s => s.Structure.Id == structure.Id && s.Type == DVHEstimateType.Upper);
                lowEstDVH = plan.DVHEstimates.FirstOrDefault(s => s.Structure.Id == structure.Id && s.Type == DVHEstimateType.Lower);

                if (upEstDVH == null || lowEstDVH == null)
                {
                    CurveData = null;
                    return;
                }

                //TODO calc these from estimated DVH
                MaxDose  = 0;
                MeanDose = 0;

                DoseUnit  = (MyDVHData.DoseUnits)lowEstDVH.CurveData[0].DoseValue.Unit;
                CurveData = new DVHPoint[lowEstDVH.CurveData.Count()];
                for (int i = 0; i < lowEstDVH.CurveData.Count(); i++)
                {
                    double dose   = lowEstDVH.CurveData[i].DoseValue.Dose;
                    double volume = 0.5 * (lowEstDVH.CurveData[i].Volume + upEstDVH.CurveData[i].Volume);
                    CurveData[i] = new DVHPoint
                    {
                        Dose   = dose,
                        Volume = volume
                    };
                }
            }
            else
            {
                apiDVH = plan.GetDVHCumulativeData(structure, dosePresentation, volPresentation, BinSize);



                if (apiDVH == null)
                {
                    MessageBox.Show("Plan " + plan.Id + " contains no dose\nCannot calculate metrics", "Invalid data", MessageBoxButton.OK, MessageBoxImage.Information);
                    return;
                }
                MaxDose  = apiDVH.MaxDose.Dose;
                MeanDose = apiDVH.MeanDose.Dose;

                DoseUnit  = (MyDVHData.DoseUnits)apiDVH.CurveData[0].DoseValue.Unit;
                CurveData = new DVHPoint[apiDVH.CurveData.Count()];
                for (int i = 0; i < apiDVH.CurveData.Count(); i++)
                {
                    CurveData[i] = new DVHPoint
                    {
                        Dose   = apiDVH.CurveData[i].DoseValue.Dose,
                        Volume = apiDVH.CurveData[i].Volume
                    };
                }
            }
        }