Example #1
0
        public static TargetIndices CalculateIndices(StructureMeta gtv, DoseMatrix dd, double prescriptionDose)
        {
            var cropped = dd.Clone();

            cropped.CropMatrixToStructure(gtv, 20);

            var presVol = cropped.ConvertIsodoseLevelToMesh(prescriptionDose).CalculateVolumeCC();
            var halfVol = cropped.ConvertIsodoseLevelToMesh(prescriptionDose / 2).CalculateVolumeCC();

            var dvh        = cropped.CalcDVH();
            var points     = dvh.GetDVHData().Points;
            var test       = points.GetVolumeAtDose(prescriptionDose);
            var dosevol    = dvh.GetDVHData().Points.GetVolumeAtDose(prescriptionDose) / 100 * cropped.VolumeCC();
            var gradVol    = dvh.GetDVHData().Points.GetVolumeAtDose(prescriptionDose / 2) / 100 * cropped.VolumeCC();
            var isodoseDef = new IsodoseLevel()
            {
                Value = prescriptionDose, Color = new Scalar(0, 0, 255)
            };
            var isoStructure = cropped.Find2DIsodoseLines(isodoseDef).First();

            isoStructure.Look = StructureLooks.Purple;
            //var vol = isoStructure.CalculateVolumeCC();
            //var gtvVol = gtv.CalculateVolumeCC();
            var ci = presVol / 5;// gtvVol;
            //var ci2 = tvol / gtvVol;
            var gi = halfVol / dosevol;

            return(new TargetIndices()
            {
                Gradient = gi,
                RTOGCI = ci,
            });
        }
        public void GeneratePDD()
        {
            DoseMatrix sourceMatrix = _source.DoseMatrix();
            DoseMatrix targetMatrix = _target.DoseMatrix();
            double     yMin         = (sourceMatrix.Y0 > targetMatrix.Y0) ? sourceMatrix.Y0 : targetMatrix.Y0;
            double     yMax         = (sourceMatrix.YMax < targetMatrix.YMax) ? sourceMatrix.YMax : targetMatrix.YMax;
            double     yRes         = sourceMatrix.YRes;

            EvilDICOM.Core.Helpers.Vector3 startPoint = new EvilDICOM.Core.Helpers.Vector3(0, yMin, 0);
            EvilDICOM.Core.Helpers.Vector3 endPoint   = new EvilDICOM.Core.Helpers.Vector3(0, yMax, 0);
            SourcePDD = sourceMatrix.GetLineDose(startPoint, endPoint, yRes);
            TargetPDD = targetMatrix.GetLineDose(startPoint, endPoint, yRes);
        }
Example #3
0
        private static Mat ProjectDoseToZPlaneMM(DoseMatrix d1, ImageMatrix im, double imagePlaneZ)
        {
            var projected = new float[im.DimensionX * im.DimensionY];

            var planeOrigin = im.Origin.Copy();

            planeOrigin.Z = imagePlaneZ;

            if (planeOrigin.Z >= d1.Origin.Z && planeOrigin.Z <= d1.ZMax)//Within dose Z bounds
            {
                //Extract dose at that plane
                var zPlane = d1.GetZPlane(planeOrigin.Z);

                //Pad image
                var x1Padmm = d1.Origin.X - im.Origin.X;
                var x2Padmm = im.XMax - d1.XMax;
                var y1Padmm = d1.Origin.Y - im.Origin.Y;
                var y2Padmm = im.YMax - d1.YMax;

                var x1Pad = (int)Math.Ceiling(x1Padmm / d1.XRes);
                var x2Pad = (int)Math.Ceiling(x2Padmm / d1.XRes);
                var y1Pad = (int)Math.Ceiling(y1Padmm / d1.YRes);
                var y2Pad = (int)Math.Ceiling(y2Padmm / d1.YRes);

                try
                {
                    zPlane = zPlane.CopyMakeBorder(y1Pad, y2Pad, x1Pad, x2Pad, BorderTypes.Constant, new Scalar(0));
                    //Calculate origin of new image
                    var x0         = d1.Origin.X - x1Pad * d1.XRes;
                    var y0         = d1.Origin.Y - y1Pad * d1.YRes;
                    var xCenter    = ((im.XMax - im.Origin.X) / 2) + im.Origin.X;
                    var yCenter    = ((im.YMax - im.Origin.Y) / 2) + im.Origin.Y;
                    var xCenterPix = (float)((xCenter - x0) / d1.XRes * d1.XRes / im.XRes);
                    var yCenterPix = (float)((yCenter - y0) / d1.YRes * d1.YRes / im.YRes);

                    //Scale to same resolution
                    zPlane = zPlane.Resize(Size.Zero, d1.XRes / im.XRes, d1.YRes / im.YRes);

                    Mat projectedMat = new Mat();
                    Cv2.GetRectSubPix(zPlane, new Size(im.DimensionX, im.DimensionY), new Point2f(xCenterPix, yCenterPix), projectedMat);
                    return(projectedMat);
                }
                catch (Exception e)
                {
                    throw new NotFiniteNumberException();
                }
            }

            //Return empty plane
            return(new Mat(im.DimensionY, im.DimensionX, MatType.CV_32FC1, projected));
        }
 /// <summary>
 /// Returns the Dose Matrix object for advanced evaluation
 /// </summary>
 /// <returns></returns>
 /// <exception cref="InvalidOperationException">Cannot call for dose on a Dicom file that is not a dose file</exception>
 public DoseMatrix DoseMatrix()
 {
     if (IsDoseFile)
     {
         DICOMObject dcm1      = DICOMObject.Read(FileName);
         DoseMatrix  dcmMatrix = new DoseMatrix(dcm1);
         X = dcmMatrix.DimensionX;
         Y = dcmMatrix.DimensionY;
         Z = dcmMatrix.DimensionZ;
         return(dcmMatrix);
     }
     else
     {
         throw new InvalidOperationException("Cannot call for dose on a Dicom file that is not a dose file");
     }
 }
Example #5
0
        public static DoseMatrix ResampleToImage(this DoseMatrix d1, ImageMatrix im)
        {
            var dm = new DoseMatrix();

            dm.Origin             = im.Origin;
            dm.PlanUID            = d1.PlanUID;
            dm.BytesAllocated     = d1.BytesAllocated;
            dm.DimensionX         = im.DimensionX;
            dm.DimensionY         = im.DimensionY;
            dm.DimensionZ         = im.DimensionZ;
            dm.XRes               = im.XRes;
            dm.YRes               = im.YRes;
            dm.ZRes               = im.ZRes;
            dm.PrescriptionDoseGy = d1.PrescriptionDoseGy;
            dm.DoseUnit           = d1.DoseUnit;
            var values = new float[dm.DimensionX * dm.DimensionY * dm.DimensionZ];

            var imageSlices = Enumerable.Range(0, im.DimensionZ).Select(i =>
            {
                return(new { Z = i * im.ZRes + im.Origin.Z, NSlice = i });
            }).ToList();

            foreach (var slice in imageSlices)
            {
                using (var mat = ProjectDoseToZPlaneMM(d1, im, slice.Z))
                {
                    var projected = new float[im.DimensionX * im.DimensionY];
                    mat.GetArray(out projected);

                    var indexStart = IndexHelper.LatticeXYZToIndex(0, 0, slice.NSlice, dm.DimensionX, dm.DimensionY);
                    var indexEnd   = projected.Length;
                    for (int i = 0; i < projected.Length; i++)
                    {
                        values[i + indexStart] = projected[i];
                    }
                }
            }

            dm.MaxDose = values.Max();
            var indexOfMax = values.ToList().IndexOf(dm.MaxDose);

            var(_, _, z)        = IndexHelper.IndexToLatticeXYZ(indexOfMax, dm.DimensionX, dm.DimensionY);
            dm.MaxDoseSlice     = z;
            dm.ImageOrientation = (d1.ImageOrientation.xDir.Copy(), d1.ImageOrientation.yDir.Copy(), d1.ImageOrientation.zDir.Copy());
            dm.CreateMatrix(values);
            return(dm);
        }
Example #6
0
 public DoseMatrixOptimal(DoseMatrix doseMatrix)
 {
     DimensionX   = doseMatrix.DimensionX;
     DimensionY   = doseMatrix.DimensionY;
     DimensionZ   = doseMatrix.DimensionZ;
     DoseValues   = doseMatrix.DoseValues.ToArray();
     Scaling      = doseMatrix.Scaling;
     X0           = doseMatrix.X0;
     Y0           = doseMatrix.Y0;
     Z0           = doseMatrix.Z0;
     XMax         = doseMatrix.XMax;
     YMax         = doseMatrix.YMax;
     ZMax         = doseMatrix.ZMax;
     XRes         = doseMatrix.XRes;
     YRes         = doseMatrix.YRes;
     ZRes         = doseMatrix.ZRes;
     Length       = DoseValues.Length;
     Count        = Length;
     MaxPointDose = doseMatrix.MaxPointDose;
 }
 public DoseMatrixOptimal(DoseMatrix doseMatrix)
 {
     if (doseMatrix == null)
     {
         throw new ArgumentNullException(nameof(doseMatrix));
     }
     DimensionX   = doseMatrix.DimensionX;
     DimensionY   = doseMatrix.DimensionY;
     DimensionZ   = doseMatrix.DimensionZ;
     DoseValues   = doseMatrix.DoseValues.ToArray();
     Scaling      = doseMatrix.Scaling;
     X0           = doseMatrix.X0;
     Y0           = doseMatrix.Y0;
     Z0           = doseMatrix.Z0;
     XMax         = doseMatrix.XMax;
     YMax         = doseMatrix.YMax;
     ZMax         = doseMatrix.ZMax;
     XRes         = doseMatrix.XRes;
     YRes         = doseMatrix.YRes;
     ZRes         = doseMatrix.ZRes;
     Length       = DoseValues.Length;
     Count        = Length;
     MaxPointDose = doseMatrix.MaxPointDose;
 }
Example #8
0
        public static DoseMatrix ParseDICOM(string dcmFile, double?prescribedDoseGy = null, bool convertToRelative = true)
        {
            var dcm = DICOMObject.Read(dcmFile);

            var matrix = new DoseMatrix();

            matrix.PrescriptionDoseGy = prescribedDoseGy;

            FillMetadata(matrix, dcm);

            //SET METADATA
            var sel = dcm.GetSelector();

            matrix.ZRes = sel.GridFrameOffsetVector.Data_[1] - sel.GridFrameOffsetVector.Data_[0];
            var offsets = sel.GridFrameOffsetVector.Data_;

            matrix.DoseUnit = sel.Dose​Units.Data == "GY" ? DoseUnit.ABSOLUTE :
                              DoseUnit.RELATIVE;
            var sumType = sel.DoseSummationType.Data;

            matrix.SumType = sumType == "PLAN" ? DoseSumType.PLAN : DoseSumType.BEAM;
            matrix.PlanUID = dcm.GetSelector().ReferencedRTPlanSequence?.Items.FirstOrDefault()?
                             .GetSelector().ReferencedSOPInstanceUID.Data;
            matrix.DimensionZ = sel.NumberOfFrames.Data;

            //FILL VOXELS
            Func <BinaryReader, float> valueConverter = null;

            switch (matrix.BytesAllocated)
            {
            case 1: valueConverter = (br) => (int)br.ReadByte(); break;

            case 2: valueConverter = (br) => br.ReadInt16(); break;

            case 4: valueConverter = (br) => br.ReadInt32(); break;

            case 8: valueConverter = (br) => br.ReadInt64(); break;
            }

            var m = dcm.GetSelector().DoseGridScaling.Data;

            if (convertToRelative && matrix.DoseUnit != DoseUnit.RELATIVE && prescribedDoseGy.HasValue)
            {
                m = m / prescribedDoseGy.Value;
                matrix.DoseUnit = DoseUnit.RELATIVE;
            }

            var values = new List <float>();

            using (BinaryReader br = new BinaryReader(dcm.GetPixelStream()))
            {
                while (br.BaseStream.Position < br.BaseStream.Length)
                {
                    values.Add((float)(m * valueConverter(br)));
                }
            }

            //CALCULATE DOSE STATS
            matrix.MaxDose = values.Max();
            var indexOfMax = values.IndexOf(matrix.MaxDose);

            var(_, _, z)        = IndexHelper.IndexToLatticeXYZ(indexOfMax, matrix.DimensionX, matrix.DimensionY);
            matrix.MaxDoseSlice = z;
            matrix.CreateMatrix(values.ToArray());
            return(matrix);
        }