/// <summary> /// Recalculates the group lengths for all groups in the <paramref name="dataset"/>. Removes any group lengths for groups with out elements. /// </summary> /// <remarks>For most use cases, this method will be called by the library as needed and will not need to be called by the user.</remarks> /// <param name="dataset">DICOM dataset</param> /// <param name="createIfMissing">If set to <c>true</c>, group length elements will be created if missing. If set to <c>false</c>, only groups with existing group lengths will be recalculated.</param> public static void RecalculateGroupLengths(this DicomDataset dataset, bool createIfMissing = true) { // recalculate group lengths for sequences first foreach (var sq in dataset.Where(x => x.ValueRepresentation == DicomVR.SQ).Cast<DicomSequence>()) { foreach (var item in sq.Items) { item.RecalculateGroupLengths(createIfMissing); } } var calculator = new DicomWriteLengthCalculator(dataset.InternalTransferSyntax, DicomWriteOptions.Default); IEnumerable<ushort> groups = null; if (createIfMissing) groups = dataset.Select(x => x.Tag.Group).Distinct(); else groups = dataset.Where(x => x.Tag.Element == 0x0000).Select(x => x.Tag.Group); foreach (var group in groups.ToList()) { var items = dataset.EnumerateGroup(group).ToList(); if (items.Count == 0) { // no items exist for the specified group; remove dataset.Remove(new DicomTag(group, 0x0000)); return; } uint length = calculator.Calculate(items); dataset.Add(new DicomTag(group, 0x0000), length); } }
public bool OnBeginSequenceItem(DicomDataset dataset) { uint length = UndefinedLength; if (_options.ExplicitLengthSequenceItems) { DicomWriteLengthCalculator calc = new DicomWriteLengthCalculator(_syntax, _options); length = calc.Calculate(dataset); } WriteTagHeader(DicomTag.Item, DicomVR.NONE, length); return true; }
/// <summary> /// Handler for traversing beginning of sequence item. /// </summary> /// <param name="dataset">Item dataset.</param> /// <returns>true if traversing completed without issues, false otherwise.</returns> /// <remarks>On false return value, the method will invoke the callback method passed in <see cref="IDicomDatasetWalker.OnBeginWalk"/> before returning.</remarks> public bool OnBeginSequenceItem(DicomDataset dataset) { uint length = UndefinedLength; if (_options.ExplicitLengthSequenceItems) { DicomWriteLengthCalculator calc = new DicomWriteLengthCalculator(_syntax, _options); length = calc.Calculate(dataset); } WriteTagHeader(DicomTag.Item, DicomVR.NONE, length); return(true); }
public bool OnBeginSequence(DicomSequence sequence) { uint length = UndefinedLength; if (_options.ExplicitLengthSequences || sequence.Tag.IsPrivate) { DicomWriteLengthCalculator calc = new DicomWriteLengthCalculator(_syntax, _options); length = calc.Calculate(sequence); } _sequences.Push(sequence); WriteTagHeader(sequence.Tag, DicomVR.SQ, length); return true; }
/// <summary> /// Recalculates the group length element for the specified group. Removes the group length element if no elements exist for the specified group. /// </summary> /// <remarks>For most use cases, this method will be called by the library as needed and will not need to be called by the user.</remarks> /// <param name="dataset">DICOM dataset</param> /// <param name="group">DICOM tag group</param> /// <param name="createIfMissing">If set to <c>true</c>, the group length element will be created if missing. If set to <c>false</c>, the group length will only be calculated if the group length element exists.</param> public static void RecalculateGroupLength(this DicomDataset dataset, ushort group, bool createIfMissing = true) { var items = dataset.EnumerateGroup(group).ToList(); if (items.Count == 0) { // no items exist for the specified group; remove dataset.Remove(new DicomTag(group, 0x0000)); return; } var calculator = new DicomWriteLengthCalculator(dataset.InternalTransferSyntax, DicomWriteOptions.Default); uint length = calculator.Calculate(items); dataset.Add(new DicomTag(group, 0x0000), length); }
protected override void OnSave() { if (RootDirectoryRecord == null) throw new InvalidOperationException("No DICOM files added, cannot save DICOM directory"); _directoryRecordSequence.Items.Clear(); var calculator = new DicomWriteLengthCalculator(FileMetaInfo.TransferSyntax, DicomWriteOptions.Default); // ensure write length calculator does not include end of sequence item //Dataset.Remove(DicomTag.DirectoryRecordSequence); //_fileOffset = 128 + calculator.Calculate(FileMetaInfo) + calculator.Calculate(Dataset); //Add the offset for the Directory Record sequence tag itself //_fileOffset += 4;//sequence element tag if (FileMetaInfo.TransferSyntax.IsExplicitVR) { _fileOffset = 128 + calculator.Calculate(FileMetaInfo) + calculator.Calculate(Dataset); _fileOffset += 2; // vr _fileOffset += 2; // padding _fileOffset += 4; // length } else { _fileOffset = 128 + 4 + calculator.Calculate(FileMetaInfo) + calculator.Calculate(Dataset); _fileOffset += 4;//sequence element tag _fileOffset += 4; //length } AddDirectoryRecordsToSequenceItem(RootDirectoryRecord); if (RootDirectoryRecord != null) { CalculateOffsets(calculator); SetOffsets(RootDirectoryRecord); Dataset.Add<uint>(DicomTag.OffsetOfTheFirstDirectoryRecordOfTheRootDirectoryEntity, RootDirectoryRecord.Offset); var lastRoot = RootDirectoryRecord; while (lastRoot.NextDirectoryRecord != null) lastRoot = lastRoot.NextDirectoryRecord; Dataset.Add<uint>(DicomTag.OffsetOfTheLastDirectoryRecordOfTheRootDirectoryEntity, lastRoot.Offset); } else { Dataset.Add<uint>(DicomTag.OffsetOfTheFirstDirectoryRecordOfTheRootDirectoryEntity, 0); Dataset.Add<uint>(DicomTag.OffsetOfTheLastDirectoryRecordOfTheRootDirectoryEntity, 0); } }
/// <summary> /// Handler for traversing beginning of sequence. /// </summary> /// <param name="sequence">Sequence to traverse.</param> /// <returns>true if traversing completed without issues, false otherwise.</returns> /// <remarks>On false return value, the method will invoke the callback method passed in <see cref="IDicomDatasetWalker.OnBeginWalk"/> before returning.</remarks> public bool OnBeginSequence(DicomSequence sequence) { uint length = UndefinedLength; if (_options.ExplicitLengthSequences || sequence.Tag.IsPrivate) { DicomWriteLengthCalculator calc = new DicomWriteLengthCalculator(_syntax, _options); length = calc.Calculate(sequence); } _sequences.Push(sequence); WriteTagHeader(sequence.Tag, DicomVR.SQ, length); return(true); }
/// <summary> /// Recalculates the group length element for the specified group. Removes the group length element if no elements exist for the specified group. /// </summary> /// <remarks>For most use cases, this method will be called by the library as needed and will not need to be called by the user.</remarks> /// <param name="dataset">DICOM dataset</param> /// <param name="group">DICOM tag group</param> /// <param name="createIfMissing">If set to <c>true</c>, the group length element will be created if missing. If set to <c>false</c>, the group length will only be calculated if the group length element exists.</param> public static void RecalculateGroupLength(this DicomDataset dataset, ushort group, bool createIfMissing = true) { var items = dataset.EnumerateGroup(group).ToList(); if (items.Count == 0) { // no items exist for the specified group; remove dataset.Remove(new DicomTag(group, 0x0000)); return; } var calculator = new DicomWriteLengthCalculator(dataset.InternalTransferSyntax, DicomWriteOptions.Default); uint length = calculator.Calculate(items); dataset.AddOrUpdate(new DicomTag(group, 0x0000), length); }
/// <summary> /// Recalculates the group lengths for all groups in the <paramref name="dataset"/>. Removes any group lengths for groups with out elements. /// </summary> /// <remarks>For most use cases, this method will be called by the library as needed and will not need to be called by the user.</remarks> /// <param name="dataset">DICOM dataset</param> /// <param name="createIfMissing">If set to <c>true</c>, group length elements will be created if missing. If set to <c>false</c>, only groups with existing group lengths will be recalculated.</param> public static void RecalculateGroupLengths(this DicomDataset dataset, bool createIfMissing = true) { // recalculate group lengths for sequences first foreach (var sq in dataset.Where(x => x.ValueRepresentation == DicomVR.SQ).Cast <DicomSequence>()) { foreach (var item in sq.Items) { item.RecalculateGroupLengths(createIfMissing); } } var calculator = new DicomWriteLengthCalculator(dataset.InternalTransferSyntax, DicomWriteOptions.Default); IEnumerable <ushort> groups = null; if (createIfMissing) { groups = dataset.Select(x => x.Tag.Group).Distinct(); } else { groups = dataset.Where(x => x.Tag.Element == 0x0000).Select(x => x.Tag.Group); } foreach (var group in groups.ToList()) { var items = dataset.EnumerateGroup(group).ToList(); if (items.Count == 0) { // no items exist for the specified group; remove dataset.Remove(new DicomTag(group, 0x0000)); return; } uint length = calculator.Calculate(items); dataset.AddOrUpdate(new DicomTag(group, 0x0000), length); } }
private void CalculateOffsets(DicomWriteLengthCalculator calculator) { foreach (var item in Dataset.Get<DicomSequence>(DicomTag.DirectoryRecordSequence)) { var record = item as DicomDirectoryRecord; if (record == null) throw new InvalidOperationException("Unexpected type for directory record: " + item.GetType()); record.Offset = _fileOffset; _fileOffset += 4 + 4;//Sequence item tag; _fileOffset += calculator.Calculate(record); _fileOffset += 4 + 4; // Sequence Item Delimitation Item } _fileOffset += 4 + 4; // Sequence Delimitation Item }