public KeyImageContentItem(string imageSopInstanceUid, string presentationSopInstanceUid, KeyObjectSelectionDocumentIod source) { this.ReferencedImageSopInstanceUid = imageSopInstanceUid; this.PresentationStateSopInstanceUid = presentationSopInstanceUid; this.FrameNumber = null; this._source = source; }
/// <summary> /// Creates the presentation images for a given key object selection document. /// </summary> /// <param name="keyObjectDocument">The key object selection document from which presentation images are to be created.</param> /// <returns>A list of created presentation images.</returns> protected virtual List <IPresentationImage> CreateImages(KeyObjectSelectionDocumentIod keyObjectDocument) { List <IPresentationImage> images = new List <IPresentationImage>(); if (_studyTree == null) { Platform.Log(LogLevel.Warn, "Key object document cannot be used to create images because there is no study tree to build from."); } else { IList <IKeyObjectContentItem> content = new KeyImageDeserializer(keyObjectDocument).Deserialize(); var evidence = new HierarchicalSopInstanceReferenceDictionary(keyObjectDocument.KeyObjectDocument.CurrentRequestedProcedureEvidenceSequence); foreach (IKeyObjectContentItem item in content) { if (item is KeyImageContentItem) { images.AddRange(CreateImages((KeyImageContentItem)item, evidence)); } else { Platform.Log(LogLevel.Warn, "Unsupported key object content value type"); } } } return(images); }
/// <summary> /// Creates the presentation images for a given key object selection document. /// </summary> /// <param name="keyObjectDocument">The key object selection document from which presentation images are to be created.</param> /// <returns>A list of created presentation images.</returns> protected virtual List <IPresentationImage> CreateImages(KeyObjectSelectionDocumentIod keyObjectDocument) { List <IPresentationImage> images = new List <IPresentationImage>(); if (_studyTree == null) { Platform.Log(LogLevel.Warn, "Key object document cannot be used to create images because there is no study tree to build from."); } else { IList <IKeyObjectContentItem> content = new KeyImageDeserializer(keyObjectDocument).Deserialize(); foreach (IKeyObjectContentItem item in content) { if (item is KeyImageContentItem) { images.AddRange(CreateImages((KeyImageContentItem)item)); } else { Platform.Log(LogLevel.Warn, "Unsupported key object content value type"); } } } return(images); }
/// <summary> /// Creates the presentation images for a given key object selection document. /// </summary> /// <param name="keyObjectDocument">The key object selection document from which presentation images are to be created.</param> /// <returns>A list of created presentation images.</returns> protected virtual List <IPresentationImage> CreateImages(KeyObjectSelectionDocumentIod keyObjectDocument) { List <IPresentationImage> images = new List <IPresentationImage>(); if (_studyTree == null) { Platform.Log(LogLevel.Warn, "Key object document cannot be used to create images because there is no study tree to build from."); } else { try { IList <IKeyObjectContentItem> content = new KeyImageDeserializer(keyObjectDocument).Deserialize(); var evidence = new HierarchicalSopInstanceReferenceDictionary(keyObjectDocument.KeyObjectDocument.CurrentRequestedProcedureEvidenceSequence); foreach (IKeyObjectContentItem item in content) { try { var contentItem = item as KeyImageContentItem; if (contentItem != null) { images.AddRange(CreateImages(contentItem, evidence)); } else { Platform.Log(LogLevel.Warn, "Unsupported key object content value type"); } } catch (Exception ex) { // catches KO errors with individual content items, allowing as many items as possible to be created Platform.Log(LogLevel.Warn, ex, SR.MessageKeyObjectDeserializeFailure); } } } catch (Exception ex) { // catches KO errors with the entire document Platform.Log(LogLevel.Warn, ex, SR.MessageKeyObjectDeserializeFailure); } } // return a KO error placeholder, otherwise the sop will be treated later as an unsupported sop class if (images.Count == 0 && keyObjectDocument.DataSource is Sop) { images.Add(PlaceholderDisplaySetFactory.CreatePlaceholderImage((Sop)keyObjectDocument.DataSource, SR.MessageKeyObjectDeserializeFailure)); } return(images); }
public KeyImageContentItem(string imageSopInstanceUid, int frameNumber, string presentationSopInstanceUid, KeyObjectSelectionDocumentIod source) : this(imageSopInstanceUid, presentationSopInstanceUid, source) { this.FrameNumber = frameNumber; }
/// <summary> /// Constructs a new instance of <see cref="KeyImageDeserializer"/>. /// </summary> /// <remarks> /// <para>Due to the relatively new nature of key object support in the ClearCanvas Framework, this API may be more prone to changes in the next release.</para> /// </remarks> public KeyImageDeserializer(KeyObjectSelectionDocumentIod iod) { _document = iod; }
/// <summary> /// Constructs a new instance of <see cref="KeyImageDeserializer"/>. /// </summary> /// <remarks> /// <para>Due to the relatively new nature of key object support in the ClearCanvas Framework, this API may be more prone to changes in the next release.</para> /// </remarks> public KeyImageDeserializer(Sop sourceSop) { _document = new KeyObjectSelectionDocumentIod(sourceSop.DataSource); }
/// <summary> /// Serializes the current contents into a number of key object selection document SOP instances. /// </summary> /// <param name="callback">A callback method to initialize the series-level attributes of the key object document. /// Should return a data set from which patient and study level attributes can be copied, otherwise a KO document will not be created for this study. /// </param> public List <DicomFile> Serialize(InitializeKeyObjectDocumentSeriesCallback callback) { callback = callback ?? DefaultInitializeKeyObjectDocumentSeriesCallback; if (_framePresentationStates.Count == 0) { throw new InvalidOperationException("Key object selection cannot be empty."); } List <DicomFile> keyObjectDocuments = new List <DicomFile>(); List <SopInstanceReference> identicalDocuments = new List <SopInstanceReference>(); Dictionary <string, KeyObjectSelectionDocumentIod> koDocumentsByStudy = new Dictionary <string, KeyObjectSelectionDocumentIod>(); foreach (var frame in (IEnumerable <KeyImageReference>)_framePresentationStates) { string studyInstanceUid = frame.StudyInstanceUid; if (!koDocumentsByStudy.ContainsKey(studyInstanceUid)) { KeyObjectDocumentSeries seriesInfo = new KeyObjectDocumentSeries(studyInstanceUid); var prototypeDataSet = callback.Invoke(seriesInfo); if (prototypeDataSet == null) { continue; } DicomFile keyObjectDocument = new DicomFile(); keyObjectDocument.SourceApplicationEntityTitle = frame.SourceApplicationEntityTitle; _sopInstanceFactory.InitializeDataSet(prototypeDataSet, keyObjectDocument.DataSet); KeyObjectSelectionDocumentIod iod = new KeyObjectSelectionDocumentIod(keyObjectDocument.DataSet); iod.GeneralEquipment.Manufacturer = this.Manufacturer ?? string.Empty; // this one is type 2 - all other GenEq attributes are type 3 iod.GeneralEquipment.ManufacturersModelName = string.IsNullOrEmpty(this.ManufacturersModelName) ? null : this.ManufacturersModelName; iod.GeneralEquipment.DeviceSerialNumber = string.IsNullOrEmpty(this.DeviceSerialNumber) ? null : this.DeviceSerialNumber; iod.GeneralEquipment.SoftwareVersions = string.IsNullOrEmpty(this.SoftwareVersions) ? null : this.SoftwareVersions; iod.GeneralEquipment.InstitutionName = string.IsNullOrEmpty(this.Institution.Name) ? null : this.Institution.Name; iod.GeneralEquipment.InstitutionAddress = string.IsNullOrEmpty(this.Institution.Address) ? null : this.Institution.Address; iod.GeneralEquipment.InstitutionalDepartmentName = string.IsNullOrEmpty(this.Institution.DepartmentName) ? null : this.Institution.DepartmentName; iod.GeneralEquipment.StationName = string.IsNullOrEmpty(this.StationName) ? null : this.StationName; iod.KeyObjectDocumentSeries.InitializeAttributes(); iod.KeyObjectDocumentSeries.Modality = Modality.KO; iod.KeyObjectDocumentSeries.SeriesDateTime = seriesInfo.SeriesDateTime; iod.KeyObjectDocumentSeries.SeriesDescription = SeriesDescription; iod.KeyObjectDocumentSeries.SeriesInstanceUid = CreateUid(seriesInfo.SeriesInstanceUid); iod.KeyObjectDocumentSeries.SeriesNumber = seriesInfo.SeriesNumber ?? 1; iod.KeyObjectDocumentSeries.ReferencedPerformedProcedureStepSequence = null; iod.SopCommon.SopClass = SopClass.KeyObjectSelectionDocumentStorage; iod.SopCommon.SopInstanceUid = DicomUid.GenerateUid().UID; identicalDocuments.Add(new SopInstanceReference( studyInstanceUid, iod.KeyObjectDocumentSeries.SeriesInstanceUid, iod.SopCommon.SopClassUid, iod.SopCommon.SopInstanceUid)); koDocumentsByStudy.Add(studyInstanceUid, iod); keyObjectDocuments.Add(keyObjectDocument); } } foreach (KeyObjectSelectionDocumentIod iod in koDocumentsByStudy.Values) { iod.KeyObjectDocument.InitializeAttributes(); iod.KeyObjectDocument.InstanceNumber = 1; iod.KeyObjectDocument.ContentDateTime = DateTime; iod.KeyObjectDocument.ReferencedRequestSequence = null; // only add docuemnts other than current to the identical documents sequence (and if there's only one, it's obviously the current) if (identicalDocuments.Count > 1) { var identicalDocumentsSequence = new HierarchicalSopInstanceReferenceDictionary(); var thisDocument = new SopInstanceReference(iod.GeneralStudy.StudyInstanceUid, iod.KeyObjectDocumentSeries.SeriesInstanceUid, iod.SopCommon.SopClassUid, iod.SopCommon.SopInstanceUid); foreach (var otherDocument in identicalDocuments.Where(d => !d.Equals(thisDocument))) { identicalDocumentsSequence.AddReference(otherDocument.StudyInstanceUid, otherDocument.SeriesInstanceUid, otherDocument.SopClassUid, otherDocument.SopInstanceUid); } iod.KeyObjectDocument.IdenticalDocumentsSequence = identicalDocumentsSequence; } iod.SrDocumentContent.InitializeContainerAttributes(); iod.SrDocumentContent.ConceptNameCodeSequence = DocumentTitle; List <IContentSequence> contentList = new List <IContentSequence>(); EvidenceDictionary currentRequestedProcedureEvidenceList = new EvidenceDictionary(); List <KeyImageReference> frameMap = new List <KeyImageReference>(); foreach (var frameAndPresentationState in _framePresentationStates) { var frame = frameAndPresentationState.Key; // build frame map by unique sop - used to make the evidence sequence less verbose if (!frameMap.Contains(frame)) { frameMap.Add(frame); } // content sequence must still list all content as it was given, including any repeats IContentSequence content = iod.SrDocumentContent.CreateContentSequence(); { content.RelationshipType = RelationshipType.Contains; IImageReferenceMacro imageReferenceMacro = content.InitializeImageReferenceAttributes(); imageReferenceMacro.ReferencedSopSequence.InitializeAttributes(); imageReferenceMacro.ReferencedSopSequence.ReferencedSopClassUid = frame.SopClassUid; imageReferenceMacro.ReferencedSopSequence.ReferencedSopInstanceUid = frame.SopInstanceUid; if (frame.FrameNumber.HasValue) { imageReferenceMacro.ReferencedSopSequence.ReferencedFrameNumber = frame.FrameNumber.Value.ToString(CultureInfo.InvariantCulture); } else { imageReferenceMacro.ReferencedSopSequence.ReferencedFrameNumber = null; } // save the presentation state if (frameAndPresentationState.Value != null) { var presentationState = frameAndPresentationState.Value; imageReferenceMacro.ReferencedSopSequence.CreateReferencedSopSequence(); imageReferenceMacro.ReferencedSopSequence.ReferencedSopSequence.InitializeAttributes(); imageReferenceMacro.ReferencedSopSequence.ReferencedSopSequence.ReferencedSopClassUid = presentationState.SopClassUid; imageReferenceMacro.ReferencedSopSequence.ReferencedSopSequence.ReferencedSopInstanceUid = presentationState.SopInstanceUid; } } contentList.Add(content); } // add the author if (!string.IsNullOrEmpty(Author)) { IContentSequence koAuthor = iod.SrDocumentContent.CreateContentSequence(); koAuthor.InitializeAttributes(); koAuthor.ConceptNameCodeSequence = KeyObjectSelectionCodeSequences.PersonObserverName; koAuthor.PersonName = Author; koAuthor.RelationshipType = RelationshipType.HasObsContext; contentList.Add(koAuthor); } // add the description if (!string.IsNullOrEmpty(Description)) { IContentSequence koDescription = iod.SrDocumentContent.CreateContentSequence(); koDescription.InitializeAttributes(); koDescription.ConceptNameCodeSequence = KeyObjectSelectionCodeSequences.KeyObjectDescription; koDescription.TextValue = Description; koDescription.RelationshipType = RelationshipType.Contains; contentList.Add(koDescription); } // add each unique sop to the evidence list using the map built earlier foreach (var sop in frameMap.Distinct()) { currentRequestedProcedureEvidenceList.Add(sop); } // add each referenced presentation state to the evidence list as well foreach (var state in (IEnumerable <PresentationStateReference>)_framePresentationStates) { if (state == null) { continue; } currentRequestedProcedureEvidenceList.Add(state); } // set the content and the evidence sequences iod.SrDocumentContent.ContentSequence = contentList.ToArray(); iod.KeyObjectDocument.CurrentRequestedProcedureEvidenceSequence = currentRequestedProcedureEvidenceList.ToArray(); } // set meta for the files foreach (DicomFile keyObjectDocument in keyObjectDocuments) { keyObjectDocument.MediaStorageSopClassUid = keyObjectDocument.DataSet[DicomTags.SopClassUid].ToString(); keyObjectDocument.MediaStorageSopInstanceUid = keyObjectDocument.DataSet[DicomTags.SopInstanceUid].ToString(); } return(keyObjectDocuments); }
private static KeyObjectSelectionDocumentIod CreatePrototypeDocument(IDicomAttributeProvider source, DicomAttributeCollection target, string specificCharacterSet) { KeyObjectSelectionDocumentIod iod = new KeyObjectSelectionDocumentIod(target); specificCharacterSet = specificCharacterSet ?? string.Empty; target.SpecificCharacterSet = specificCharacterSet; target[DicomTags.SpecificCharacterSet].SetStringValue(specificCharacterSet); PatientModuleIod sourcePatient = new PatientModuleIod(source); if (true) // patient module is always required { iod.Patient.BreedRegistrationSequence = sourcePatient.BreedRegistrationSequence; iod.Patient.DeIdentificationMethod = sourcePatient.DeIdentificationMethod; iod.Patient.DeIdentificationMethodCodeSequence = sourcePatient.DeIdentificationMethodCodeSequence; iod.Patient.EthnicGroup = sourcePatient.EthnicGroup; iod.Patient.IssuerOfPatientId = sourcePatient.IssuerOfPatientId; iod.Patient.OtherPatientIds = sourcePatient.OtherPatientIds; iod.Patient.OtherPatientIdsSequence = sourcePatient.OtherPatientIdsSequence; iod.Patient.OtherPatientNames = sourcePatient.OtherPatientNames; iod.Patient.PatientBreedCodeSequence = sourcePatient.PatientBreedCodeSequence; iod.Patient.PatientBreedDescription = sourcePatient.PatientBreedDescription; iod.Patient.PatientComments = sourcePatient.PatientComments; iod.Patient.PatientId = sourcePatient.PatientId; iod.Patient.PatientIdentityRemoved = sourcePatient.PatientIdentityRemoved; iod.Patient.PatientsBirthDateTime = sourcePatient.PatientsBirthDateTime; iod.Patient.PatientsName = sourcePatient.PatientsName; iod.Patient.PatientSpeciesCodeSequence = sourcePatient.PatientSpeciesCodeSequence; iod.Patient.PatientSpeciesDescription = sourcePatient.PatientSpeciesDescription; iod.Patient.PatientsSex = sourcePatient.PatientsSex; iod.Patient.ReferencedPatientSequence = sourcePatient.ReferencedPatientSequence; iod.Patient.ResponsibleOrganization = sourcePatient.ResponsibleOrganization; iod.Patient.ResponsiblePerson = sourcePatient.ResponsiblePerson; iod.Patient.ResponsiblePersonRole = sourcePatient.ResponsiblePersonRole; } SpecimenIdentificationModuleIod sourceSpecimen = new SpecimenIdentificationModuleIod(source); if (sourceSpecimen.HasValues()) // specimen module is required only if subject is a specimen { iod.SpecimenIdentification.SpecimenAccessionNumber = sourceSpecimen.SpecimenAccessionNumber; iod.SpecimenIdentification.SpecimenSequence = sourceSpecimen.SpecimenSequence; } ClinicalTrialSubjectModuleIod sourceTrialSubject = new ClinicalTrialSubjectModuleIod(source); if (sourceTrialSubject.HasValues()) // clinical trial subkect module is user optional { iod.ClinicalTrialSubject.ClinicalTrialProtocolId = sourceTrialSubject.ClinicalTrialProtocolId; iod.ClinicalTrialSubject.ClinicalTrialProtocolName = sourceTrialSubject.ClinicalTrialProtocolName; iod.ClinicalTrialSubject.ClinicalTrialSiteId = sourceTrialSubject.ClinicalTrialSiteId; iod.ClinicalTrialSubject.ClinicalTrialSiteName = sourceTrialSubject.ClinicalTrialSiteName; iod.ClinicalTrialSubject.ClinicalTrialSponsorName = sourceTrialSubject.ClinicalTrialSponsorName; iod.ClinicalTrialSubject.ClinicalTrialSubjectId = sourceTrialSubject.ClinicalTrialSubjectId; iod.ClinicalTrialSubject.ClinicalTrialSubjectReadingId = sourceTrialSubject.ClinicalTrialSubjectReadingId; } GeneralStudyModuleIod sourceGeneralStudy = new GeneralStudyModuleIod(source); if (true) // general study module is always required { iod.GeneralStudy.AccessionNumber = sourceGeneralStudy.AccessionNumber; iod.GeneralStudy.NameOfPhysiciansReadingStudy = sourceGeneralStudy.NameOfPhysiciansReadingStudy; iod.GeneralStudy.PhysiciansOfRecord = sourceGeneralStudy.PhysiciansOfRecord; iod.GeneralStudy.PhysiciansOfRecordIdentificationSequence = sourceGeneralStudy.PhysiciansOfRecordIdentificationSequence; iod.GeneralStudy.PhysiciansReadingStudyIdentificationSequence = sourceGeneralStudy.PhysiciansReadingStudyIdentificationSequence; iod.GeneralStudy.ProcedureCodeSequence = sourceGeneralStudy.ProcedureCodeSequence; iod.GeneralStudy.ReferencedStudySequence = sourceGeneralStudy.ReferencedStudySequence; iod.GeneralStudy.ReferringPhysicianIdentificationSequence = sourceGeneralStudy.ReferringPhysicianIdentificationSequence; iod.GeneralStudy.ReferringPhysiciansName = sourceGeneralStudy.ReferringPhysiciansName; iod.GeneralStudy.StudyDateTime = sourceGeneralStudy.StudyDateTime; iod.GeneralStudy.StudyDescription = sourceGeneralStudy.StudyDescription; iod.GeneralStudy.StudyId = sourceGeneralStudy.StudyId; iod.GeneralStudy.StudyInstanceUid = sourceGeneralStudy.StudyInstanceUid; } PatientStudyModuleIod sourcePatientStudy = new PatientStudyModuleIod(source); if (sourcePatientStudy.HasValues()) // patient study module is user optional { iod.PatientStudy.AdditionalPatientHistory = sourcePatientStudy.AdditionalPatientHistory; iod.PatientStudy.AdmissionId = sourcePatientStudy.AdmissionId; iod.PatientStudy.AdmittingDiagnosesCodeSequence = sourcePatientStudy.AdmittingDiagnosesCodeSequence; iod.PatientStudy.AdmittingDiagnosesDescription = sourcePatientStudy.AdmittingDiagnosesDescription; iod.PatientStudy.IssuerOfAdmissionId = sourcePatientStudy.IssuerOfAdmissionId; iod.PatientStudy.IssuerOfServiceEpisodeId = sourcePatientStudy.IssuerOfServiceEpisodeId; iod.PatientStudy.Occupation = sourcePatientStudy.Occupation; iod.PatientStudy.PatientsAge = sourcePatientStudy.PatientsAge; iod.PatientStudy.PatientsSexNeutered = sourcePatientStudy.PatientsSexNeutered; iod.PatientStudy.PatientsSize = sourcePatientStudy.PatientsSize; iod.PatientStudy.PatientsWeight = sourcePatientStudy.PatientsWeight; iod.PatientStudy.ServiceEpisodeDescription = sourcePatientStudy.ServiceEpisodeDescription; iod.PatientStudy.ServiceEpisodeId = sourcePatientStudy.ServiceEpisodeId; } ClinicalTrialStudyModuleIod sourceTrialStudy = new ClinicalTrialStudyModuleIod(source); if (sourceTrialStudy.HasValues()) // clinical trial study module is user optional { iod.ClinicalTrialStudy.ClinicalTrialTimePointDescription = sourceTrialStudy.ClinicalTrialTimePointDescription; iod.ClinicalTrialStudy.ClinicalTrialTimePointId = sourceTrialStudy.ClinicalTrialTimePointId; } return(iod); }
/// <summary> /// Serializes the current contents into a number of key object selection document SOP instances. /// </summary> /// <param name="callback">A callback method to initialize the series-level attributes of the key object document.</param> public List <DicomFile> Serialize(InitializeKeyObjectDocumentSeriesCallback callback) { callback = callback ?? DefaultInitializeKeyObjectDocumentSeriesCallback; if (_framePresentationStates.Count == 0) { throw new InvalidOperationException("Key object selection cannot be empty."); } List <DicomFile> keyObjectDocuments = new List <DicomFile>(); List <IHierarchicalSopInstanceReferenceMacro> identicalDocuments = new List <IHierarchicalSopInstanceReferenceMacro>(); Dictionary <string, KeyObjectSelectionDocumentIod> koDocumentsByStudy = new Dictionary <string, KeyObjectSelectionDocumentIod>(); foreach (Frame frame in (IEnumerable <Frame>)_framePresentationStates) { string studyInstanceUid = frame.StudyInstanceUid; if (!koDocumentsByStudy.ContainsKey(studyInstanceUid)) { KeyObjectDocumentSeries seriesInfo = new KeyObjectDocumentSeries(frame.ParentImageSop.PatientId, studyInstanceUid); callback.Invoke(seriesInfo); DicomFile keyObjectDocument = new DicomFile(); keyObjectDocument.SourceApplicationEntityTitle = this.SourceAETitle; KeyObjectSelectionDocumentIod iod = CreatePrototypeDocument(frame.ParentImageSop.DataSource, keyObjectDocument.DataSet, SpecificCharacterSet); iod.GeneralEquipment.Manufacturer = this.Manufacturer ?? string.Empty; // this one is type 2 - all other GenEq attributes are type 3 iod.GeneralEquipment.ManufacturersModelName = string.IsNullOrEmpty(this.ManufacturersModelName) ? null : this.ManufacturersModelName; iod.GeneralEquipment.DeviceSerialNumber = string.IsNullOrEmpty(this.DeviceSerialNumber) ? null : this.DeviceSerialNumber; iod.GeneralEquipment.SoftwareVersions = string.IsNullOrEmpty(this.SoftwareVersions) ? null : this.SoftwareVersions; iod.GeneralEquipment.InstitutionName = string.IsNullOrEmpty(this.Institution.Name) ? null : this.Institution.Name; iod.GeneralEquipment.InstitutionAddress = string.IsNullOrEmpty(this.Institution.Address) ? null : this.Institution.Address; iod.GeneralEquipment.InstitutionalDepartmentName = string.IsNullOrEmpty(this.Institution.DepartmentName) ? null : this.Institution.DepartmentName; iod.GeneralEquipment.StationName = string.IsNullOrEmpty(this.StationName) ? null : this.StationName; string seriesDescription = _seriesDescription; if (!string.IsNullOrEmpty(_author)) { seriesDescription = string.Format("{0} ({1})", seriesDescription, _author); } iod.KeyObjectDocumentSeries.InitializeAttributes(); iod.KeyObjectDocumentSeries.Modality = Modality.KO; iod.KeyObjectDocumentSeries.SeriesDateTime = seriesInfo.SeriesDateTime; iod.KeyObjectDocumentSeries.SeriesDescription = seriesDescription; iod.KeyObjectDocumentSeries.SeriesInstanceUid = CreateUid(seriesInfo.SeriesInstanceUid); iod.KeyObjectDocumentSeries.SeriesNumber = seriesInfo.SeriesNumber ?? CalculateSeriesNumber(frame); iod.KeyObjectDocumentSeries.ReferencedPerformedProcedureStepSequence = null; iod.SopCommon.SopClass = SopClass.KeyObjectSelectionDocumentStorage; iod.SopCommon.SopInstanceUid = DicomUid.GenerateUid().UID; identicalDocuments.Add(iod.KeyObjectDocument.CreateIdenticalDocumentsSequence( studyInstanceUid, iod.KeyObjectDocumentSeries.SeriesInstanceUid, iod.SopCommon.SopClassUid, iod.SopCommon.SopInstanceUid)); koDocumentsByStudy.Add(studyInstanceUid, iod); keyObjectDocuments.Add(keyObjectDocument); } } foreach (KeyObjectSelectionDocumentIod iod in koDocumentsByStudy.Values) { iod.KeyObjectDocument.InitializeAttributes(); iod.KeyObjectDocument.InstanceNumber = 1; iod.KeyObjectDocument.ContentDateTime = _datetime; iod.KeyObjectDocument.ReferencedRequestSequence = null; iod.KeyObjectDocument.IdenticalDocumentsSequence = identicalDocuments.ToArray(); iod.SrDocumentContent.InitializeContainerAttributes(); iod.SrDocumentContent.ConceptNameCodeSequence = _docTitle; List <IContentSequence> contentList = new List <IContentSequence>(); EvidenceDictionary currentRequestedProcedureEvidenceList = new EvidenceDictionary(); Dictionary <ImageSop, List <int> > frameMap = new Dictionary <ImageSop, List <int> >(); foreach (KeyValuePair <Frame, DicomSoftcopyPresentationState> frameAndPresentationState in _framePresentationStates) { Frame frame = frameAndPresentationState.Key; ImageSop sop = frame.ParentImageSop; // build frame map by unique sop - used to make the evidence sequence less verbose if (!frameMap.ContainsKey(frame.ParentImageSop)) { frameMap.Add(frame.ParentImageSop, new List <int>()); } List <int> frames = frameMap[frame.ParentImageSop]; if (!frames.Contains(frame.FrameNumber)) { frames.Add(frame.FrameNumber); } // content sequence must still list all content as it was given, including any repeats IContentSequence content = iod.SrDocumentContent.CreateContentSequence(); { content.RelationshipType = RelationshipType.Contains; content.ReferencedContentItemIdentifier = new uint[] { 1 }; IImageReferenceMacro imageReferenceMacro = content.InitializeImageReferenceAttributes(); imageReferenceMacro.ReferencedSopSequence.InitializeAttributes(); imageReferenceMacro.ReferencedSopSequence.ReferencedSopClassUid = sop.SopClassUid; imageReferenceMacro.ReferencedSopSequence.ReferencedSopInstanceUid = sop.SopInstanceUid; if (sop.NumberOfFrames > 1) { imageReferenceMacro.ReferencedSopSequence.ReferencedFrameNumber = frame.FrameNumber.ToString(); } else { imageReferenceMacro.ReferencedSopSequence.ReferencedFrameNumber = null; } // save the presentation state if (frameAndPresentationState.Value != null) { DicomSoftcopyPresentationState presentationState = frameAndPresentationState.Value; imageReferenceMacro.ReferencedSopSequence.CreateReferencedSopSequence(); imageReferenceMacro.ReferencedSopSequence.ReferencedSopSequence.InitializeAttributes(); imageReferenceMacro.ReferencedSopSequence.ReferencedSopSequence.ReferencedSopClassUid = presentationState.PresentationSopClass.Uid; imageReferenceMacro.ReferencedSopSequence.ReferencedSopSequence.ReferencedSopInstanceUid = presentationState.PresentationSopInstanceUid; } } contentList.Add(content); } // add the description if (!string.IsNullOrEmpty(_description)) { IContentSequence koDescription = iod.SrDocumentContent.CreateContentSequence(); koDescription.InitializeAttributes(); koDescription.ConceptNameCodeSequence = KeyObjectSelectionCodeSequences.KeyObjectDescription; koDescription.TextValue = _description; koDescription.RelationshipType = RelationshipType.Contains; koDescription.ReferencedContentItemIdentifier = new uint[] { 1 }; contentList.Add(koDescription); } // add each unique sop to the evidence list using the map built earlier foreach (ImageSop sop in frameMap.Keys) { currentRequestedProcedureEvidenceList.Add(sop); } // add each referenced presentation state to the evidence list as well foreach (DicomSoftcopyPresentationState state in (IEnumerable <DicomSoftcopyPresentationState>)_framePresentationStates) { if (state == null) { continue; } currentRequestedProcedureEvidenceList.Add(state); } // set the content and the evidence sequences iod.SrDocumentContent.ContentSequence = contentList.ToArray(); iod.KeyObjectDocument.CurrentRequestedProcedureEvidenceSequence = currentRequestedProcedureEvidenceList.ToArray(); } // set meta for the files foreach (DicomFile keyObjectDocument in keyObjectDocuments) { keyObjectDocument.MediaStorageSopClassUid = keyObjectDocument.DataSet[DicomTags.SopClassUid].ToString(); keyObjectDocument.MediaStorageSopInstanceUid = keyObjectDocument.DataSet[DicomTags.SopInstanceUid].ToString(); } return(keyObjectDocuments); }
public IImageProperty[] GetProperties(IPresentationImage image) { List <IImageProperty> properties = new List <IImageProperty>(); if (image != null && image.ParentDisplaySet != null) { IImageViewer viewer = image.ImageViewer; if (viewer != null) { IDicomDisplaySetDescriptor descriptor = image.ParentDisplaySet.Descriptor as IDicomDisplaySetDescriptor; if (descriptor != null && descriptor.SourceSeries != null) { string uid = descriptor.SourceSeries.SeriesInstanceUid; if (!String.IsNullOrEmpty(uid)) { StudyTree studyTree = viewer.StudyTree; Series keyObjectSeries = studyTree.GetSeries(uid); if (keyObjectSeries != null && keyObjectSeries.Sops.Count > 0) { Sop keyObjectSop = keyObjectSeries.Sops[0]; if (keyObjectSop.SopClassUid == SopClass.KeyObjectSelectionDocumentStorageUid) { KeyObjectSelectionDocumentIod iod = new KeyObjectSelectionDocumentIod(keyObjectSop); SrDocumentContentModuleIod content = iod.SrDocumentContent; GeneralEquipmentModuleIod equipment = iod.GeneralEquipment; if (content != null) { string codeValue = ""; CodeSequenceMacro conceptSequence = content.ConceptNameCodeSequence; if (conceptSequence != null) { KeyObjectSelectionDocumentTitle documentTitle = KeyObjectSelectionDocumentTitleContextGroup.LookupTitle(conceptSequence); if (documentTitle != null) { codeValue = documentTitle.ToString(); } } string documentDescription = ""; IContentSequence[] contentSequences = content.ContentSequence ?? new IContentSequence[0]; for (int i = contentSequences.Length - 1; i >= 0; --i) { IContentSequence contentSequence = contentSequences[i]; CodeSequenceMacro sequenceMacro = contentSequence.ConceptNameCodeSequence; if (sequenceMacro != null && sequenceMacro.CodeValue == KeyObjectSelectionCodeSequences.KeyObjectDescription.CodeValue) { documentDescription = contentSequence.TextValue; break; } } properties.Add( new ImageProperty("KeyImageDocumentTitle", SR.CategoryKeyImageSeries, SR.NameKeyImageDocumentTitle, SR.DescriptionKeyImageDocumentTitle, codeValue)); properties.Add( new ImageProperty("KeyImageDocumentDescription", SR.CategoryKeyImageSeries, SR.NameKeyImageDocumentDescription, SR.DescriptionKeyImageDocumentDescription, documentDescription)); properties.Add( new ImageProperty("KeyImageEquipmentManufacturer", SR.CategoryKeyImageEquipment, SR.NameManufacturer, SR.DescriptionManufacturer, equipment.Manufacturer ?? "")); properties.Add( new ImageProperty("KeyImageEquipmentManufacturersModelName", SR.CategoryKeyImageEquipment, SR.NameManufacturersModelName, SR.DescriptionManufacturersModelName, equipment.ManufacturersModelName ?? "")); properties.Add( new ImageProperty("KeyImageEquipmentSoftwareVersions", SR.CategoryKeyImageEquipment, SR.NameSoftwareVersions, SR.DescriptionSoftwareVersions, equipment.SoftwareVersions ?? "")); } } } } } } } return(properties.ToArray()); }
public KeyObjectDescriptionContentItem(string description, KeyObjectSelectionDocumentIod source) { _source = source; Description = description; }
public PersonObserverContextContentItem(string personObserverName, KeyObjectSelectionDocumentIod source) { _source = source; PersonObserverName = personObserverName; }