1use crate::header::{EmptyObject, HasLength, Length, Tag};
4use num_traits::NumCast;
5use smallvec::SmallVec;
6use std::{borrow::Cow, str::FromStr};
7
8pub mod deserialize;
9pub mod fragments;
10pub mod partial;
11pub mod person_name;
12mod primitive;
13pub mod range;
14pub mod serialize;
15
16pub use self::deserialize::Error as DeserializeError;
17pub use self::partial::{DicomDate, DicomDateTime, DicomTime, PreciseDateTime};
18pub use self::person_name::PersonName;
19pub use self::range::{AsRange, DateRange, DateTimeRange, TimeRange};
20
21pub use self::primitive::{
22 CastValueError, ConvertValueError, InvalidValueReadError, ModifyValueError, PrimitiveValue,
23 ValueType,
24};
25
26pub use either::Either;
27
28pub type C<T> = SmallVec<[T; 2]>;
30
31pub type InMemFragment = Vec<u8>;
33
34pub trait DicomValueType: HasLength {
36 fn value_type(&self) -> ValueType;
38
39 fn cardinality(&self) -> usize;
46}
47
48impl<L, R> HasLength for Either<L, R>
49where
50 L: HasLength,
51 R: HasLength,
52{
53 fn length(&self) -> Length {
54 match self {
55 Either::Left(l) => l.length(),
56 Either::Right(r) => r.length(),
57 }
58 }
59}
60
61impl<L, R> DicomValueType for Either<L, R>
62where
63 L: DicomValueType,
64 R: DicomValueType,
65{
66 fn value_type(&self) -> ValueType {
67 match self {
68 Either::Left(l) => l.value_type(),
69 Either::Right(r) => r.value_type(),
70 }
71 }
72
73 fn cardinality(&self) -> usize {
74 match self {
75 Either::Left(l) => l.cardinality(),
76 Either::Right(r) => r.cardinality(),
77 }
78 }
79}
80
81#[derive(Debug, Clone, PartialEq)]
89pub enum Value<I = EmptyObject, P = InMemFragment> {
90 Primitive(PrimitiveValue),
92 Sequence(DataSetSequence<I>),
94 PixelSequence(PixelFragmentSequence<P>),
96}
97
98impl<P> Value<EmptyObject, P> {
99 pub fn new_pixel_sequence<T>(offset_table: C<u32>, fragments: T) -> Self
113 where
114 T: Into<C<P>>,
115 {
116 Value::from(PixelFragmentSequence::new(offset_table, fragments))
117 }
118}
119
120impl<I> Value<I> {
121 #[inline]
131 pub fn new_sequence<T>(items: T, length: Length) -> Self
132 where
133 T: Into<C<I>>,
134 {
135 Self::from(DataSetSequence::new(items, length))
136 }
137}
138
139impl Value {
140 #[inline]
162 pub fn new(value: PrimitiveValue) -> Self {
163 Self::from(value)
164 }
165}
166
167impl<I, P> Value<I, P> {
168 pub fn multiplicity(&self) -> u32 {
174 match self {
175 Value::Primitive(v) => v.multiplicity(),
176 Value::Sequence(v) => v.multiplicity(),
177 Value::PixelSequence(..) => 1,
178 }
179 }
180
181 pub fn primitive(&self) -> Option<&PrimitiveValue> {
183 match self {
184 Value::Primitive(v) => Some(v),
185 _ => None,
186 }
187 }
188
189 pub fn shallow_clone(&self) -> Value<&I, &P> {
197 match self {
198 Value::Primitive(v) => Value::Primitive(v.clone()),
199 Value::Sequence(v) => Value::Sequence(DataSetSequence {
200 items: v.items.iter().collect(),
201 length: v.length,
202 }),
203 Value::PixelSequence(v) => Value::PixelSequence(PixelFragmentSequence {
204 offset_table: v.offset_table.iter().copied().collect(),
205 fragments: v.fragments.iter().collect(),
206 }),
207 }
208 }
209
210 pub fn primitive_mut(&mut self) -> Option<&mut PrimitiveValue> {
212 match self {
213 Value::Primitive(v) => Some(v),
214 _ => None,
215 }
216 }
217
218 pub fn items(&self) -> Option<&[I]> {
222 match self {
223 Value::Sequence(v) => Some(v.items()),
224 _ => None,
225 }
226 }
227
228 pub fn items_mut(&mut self) -> Option<&mut C<I>> {
232 match self {
233 Value::Sequence(v) => Some(v.items_mut()),
234 _ => None,
235 }
236 }
237
238 pub fn fragments(&self) -> Option<&[P]> {
242 match self {
243 Value::PixelSequence(v) => Some(v.fragments()),
244 _ => None,
245 }
246 }
247
248 pub fn fragments_mut(&mut self) -> Option<&mut C<P>> {
252 match self {
253 Value::PixelSequence(v) => Some(v.fragments_mut()),
254 _ => None,
255 }
256 }
257
258 pub fn into_primitive(self) -> Option<PrimitiveValue> {
260 match self {
261 Value::Primitive(v) => Some(v),
262 _ => None,
263 }
264 }
265
266 pub fn into_items(self) -> Option<C<I>> {
271 match self {
272 Value::Sequence(v) => Some(v.into_items()),
273 _ => None,
274 }
275 }
276
277 pub fn into_fragments(self) -> Option<C<P>> {
280 match self {
281 Value::PixelSequence(v) => Some(v.into_fragments()),
282 _ => None,
283 }
284 }
285
286 pub fn offset_table(&self) -> Option<&[u32]> {
290 match self {
291 Value::PixelSequence(v) => Some(v.offset_table()),
292 _ => None,
293 }
294 }
295
296 pub fn offset_table_mut(&mut self) -> Option<&mut C<u32>> {
300 match self {
301 Value::PixelSequence(v) => Some(v.offset_table_mut()),
302 _ => None,
303 }
304 }
305
306 pub fn truncate(&mut self, limit: usize) {
320 match self {
321 Value::Primitive(v) => v.truncate(limit),
322 Value::Sequence(v) => v.truncate(limit),
323 Value::PixelSequence(v) => v.truncate(limit),
324 }
325 }
326}
327
328impl<I, P> From<&str> for Value<I, P> {
329 fn from(value: &str) -> Self {
331 Value::Primitive(PrimitiveValue::from(value))
332 }
333}
334
335impl<I, P> From<String> for Value<I, P> {
336 fn from(value: String) -> Self {
338 Value::Primitive(PrimitiveValue::from(value))
339 }
340}
341
342impl<I, P> From<DicomDate> for Value<I, P> {
343 fn from(value: DicomDate) -> Self {
345 Value::Primitive(PrimitiveValue::from(value))
346 }
347}
348
349impl<I, P> From<DicomTime> for Value<I, P> {
350 fn from(value: DicomTime) -> Self {
352 Value::Primitive(PrimitiveValue::from(value))
353 }
354}
355
356impl<I, P> From<DicomDateTime> for Value<I, P> {
357 fn from(value: DicomDateTime) -> Self {
359 Value::Primitive(PrimitiveValue::from(value))
360 }
361}
362
363impl<I, P> HasLength for Value<I, P> {
364 fn length(&self) -> Length {
365 match self {
366 Value::Primitive(v) => v.length(),
367 Value::Sequence(v) => v.length(),
368 Value::PixelSequence(v) => v.length(),
369 }
370 }
371}
372
373impl<I, P> HasLength for &Value<I, P> {
374 fn length(&self) -> Length {
375 HasLength::length(*self)
376 }
377}
378
379impl<I, P> DicomValueType for Value<I, P> {
380 fn value_type(&self) -> ValueType {
381 match self {
382 Value::Primitive(v) => v.value_type(),
383 Value::Sequence(..) => ValueType::DataSetSequence,
384 Value::PixelSequence(..) => ValueType::PixelSequence,
385 }
386 }
387
388 fn cardinality(&self) -> usize {
389 match self {
390 Value::Primitive(v) => v.cardinality(),
391 Value::Sequence(DataSetSequence { items, .. }) => items.len(),
392 Value::PixelSequence { .. } => 1,
393 }
394 }
395}
396
397impl<I, P> DicomValueType for &Value<I, P> {
398 fn value_type(&self) -> ValueType {
399 DicomValueType::value_type(*self)
400 }
401
402 fn cardinality(&self) -> usize {
403 DicomValueType::cardinality(*self)
404 }
405}
406
407impl<I, P> Value<I, P>
408where
409 I: HasLength,
410{
411 pub fn to_str(&self) -> Result<Cow<'_, str>, ConvertValueError> {
422 match self {
423 Value::Primitive(prim) => Ok(prim.to_str()),
424 _ => Err(ConvertValueError {
425 requested: "string",
426 original: self.value_type(),
427 cause: None,
428 }),
429 }
430 }
431
432 pub fn to_raw_str(&self) -> Result<Cow<'_, str>, ConvertValueError> {
441 match self {
442 Value::Primitive(prim) => Ok(prim.to_raw_str()),
443 _ => Err(ConvertValueError {
444 requested: "string",
445 original: self.value_type(),
446 cause: None,
447 }),
448 }
449 }
450
451 pub fn to_multi_str(&self) -> Result<Cow<'_, [String]>, CastValueError> {
460 match self {
461 Value::Primitive(prim) => Ok(prim.to_multi_str()),
462 _ => Err(CastValueError {
463 requested: "string",
464 got: self.value_type(),
465 }),
466 }
467 }
468
469 pub fn to_bytes(&self) -> Result<Cow<'_, [u8]>, ConvertValueError> {
476 match self {
477 Value::Primitive(prim) => Ok(prim.to_bytes()),
478 _ => Err(ConvertValueError {
479 requested: "bytes",
480 original: self.value_type(),
481 cause: None,
482 }),
483 }
484 }
485
486 pub fn to_int<T>(&self) -> Result<T, ConvertValueError>
493 where
494 T: Clone,
495 T: NumCast,
496 T: FromStr<Err = std::num::ParseIntError>,
497 {
498 match self {
499 Value::Primitive(v) => v.to_int::<T>(),
500 _ => Err(ConvertValueError {
501 requested: "integer",
502 original: self.value_type(),
503 cause: None,
504 }),
505 }
506 }
507
508 pub fn to_multi_int<T>(&self) -> Result<Vec<T>, ConvertValueError>
515 where
516 T: Clone,
517 T: NumCast,
518 T: FromStr<Err = std::num::ParseIntError>,
519 {
520 match self {
521 Value::Primitive(v) => v.to_multi_int::<T>(),
522 _ => Err(ConvertValueError {
523 requested: "integer",
524 original: self.value_type(),
525 cause: None,
526 }),
527 }
528 }
529
530 pub fn to_float32(&self) -> Result<f32, ConvertValueError> {
538 match self {
539 Value::Primitive(v) => v.to_float32(),
540 _ => Err(ConvertValueError {
541 requested: "float32",
542 original: self.value_type(),
543 cause: None,
544 }),
545 }
546 }
547
548 pub fn to_multi_float32(&self) -> Result<Vec<f32>, ConvertValueError> {
556 match self {
557 Value::Primitive(v) => v.to_multi_float32(),
558 _ => Err(ConvertValueError {
559 requested: "float32",
560 original: self.value_type(),
561 cause: None,
562 }),
563 }
564 }
565
566 pub fn to_float64(&self) -> Result<f64, ConvertValueError> {
574 match self {
575 Value::Primitive(v) => v.to_float64(),
576 _ => Err(ConvertValueError {
577 requested: "float64",
578 original: self.value_type(),
579 cause: None,
580 }),
581 }
582 }
583
584 pub fn to_multi_float64(&self) -> Result<Vec<f64>, ConvertValueError> {
592 match self {
593 Value::Primitive(v) => v.to_multi_float64(),
594 _ => Err(ConvertValueError {
595 requested: "float64",
596 original: self.value_type(),
597 cause: None,
598 }),
599 }
600 }
601
602 pub fn to_date(&self) -> Result<DicomDate, ConvertValueError> {
608 match self {
609 Value::Primitive(v) => v.to_date(),
610 _ => Err(ConvertValueError {
611 requested: "DicomDate",
612 original: self.value_type(),
613 cause: None,
614 }),
615 }
616 }
617
618 pub fn to_multi_date(&self) -> Result<Vec<DicomDate>, ConvertValueError> {
624 match self {
625 Value::Primitive(v) => v.to_multi_date(),
626 _ => Err(ConvertValueError {
627 requested: "DicomDate",
628 original: self.value_type(),
629 cause: None,
630 }),
631 }
632 }
633
634 pub fn to_time(&self) -> Result<DicomTime, ConvertValueError> {
640 match self {
641 Value::Primitive(v) => v.to_time(),
642 _ => Err(ConvertValueError {
643 requested: "DicomTime",
644 original: self.value_type(),
645 cause: None,
646 }),
647 }
648 }
649
650 pub fn to_multi_time(&self) -> Result<Vec<DicomTime>, ConvertValueError> {
656 match self {
657 Value::Primitive(v) => v.to_multi_time(),
658 _ => Err(ConvertValueError {
659 requested: "DicomTime",
660 original: self.value_type(),
661 cause: None,
662 }),
663 }
664 }
665
666 pub fn to_datetime(&self) -> Result<DicomDateTime, ConvertValueError> {
672 match self {
673 Value::Primitive(v) => v.to_datetime(),
674 _ => Err(ConvertValueError {
675 requested: "DicomDateTime",
676 original: self.value_type(),
677 cause: None,
678 }),
679 }
680 }
681
682 pub fn to_multi_datetime(&self) -> Result<Vec<DicomDateTime>, ConvertValueError> {
688 match self {
689 Value::Primitive(v) => v.to_multi_datetime(),
690 _ => Err(ConvertValueError {
691 requested: "DicomDateTime",
692 original: self.value_type(),
693 cause: None,
694 }),
695 }
696 }
697
698 pub fn to_date_range(&self) -> Result<DateRange, ConvertValueError> {
704 match self {
705 Value::Primitive(v) => v.to_date_range(),
706 _ => Err(ConvertValueError {
707 requested: "DateRange",
708 original: self.value_type(),
709 cause: None,
710 }),
711 }
712 }
713
714 pub fn to_time_range(&self) -> Result<TimeRange, ConvertValueError> {
720 match self {
721 Value::Primitive(v) => v.to_time_range(),
722 _ => Err(ConvertValueError {
723 requested: "TimeRange",
724 original: self.value_type(),
725 cause: None,
726 }),
727 }
728 }
729
730 pub fn to_datetime_range(&self) -> Result<DateTimeRange, ConvertValueError> {
736 match self {
737 Value::Primitive(v) => v.to_datetime_range(),
738 _ => Err(ConvertValueError {
739 requested: "DateTimeRange",
740 original: self.value_type(),
741 cause: None,
742 }),
743 }
744 }
745
746 pub fn to_tag(&self) -> Result<Tag, CastValueError> {
748 match self {
749 Value::Primitive(PrimitiveValue::Tags(v)) => Ok(v[0]),
750 _ => Err(CastValueError {
751 requested: "tag",
752 got: self.value_type(),
753 }),
754 }
755 }
756
757 pub fn to_person_name(&self) -> Result<PersonName<'_>, ConvertValueError> {
759 match self {
760 Value::Primitive(v) => v.to_person_name(),
761 _ => Err(ConvertValueError {
762 requested: "PersonName",
763 original: self.value_type(),
764 cause: None,
765 }),
766 }
767 }
768}
769
770macro_rules! impl_primitive_getters {
775 ($name_single: ident, $name_multi: ident, $variant: ident, $ret: ty) => {
776 pub fn $name_single(&self) -> Result<$ret, CastValueError> {
782 match self {
783 Value::Primitive(v) => v.$name_single(),
784 value => Err(CastValueError {
785 requested: stringify!($name_single),
786 got: value.value_type(),
787 }),
788 }
789 }
790
791 pub fn $name_multi(&self) -> Result<&[$ret], CastValueError> {
795 match self {
796 Value::Primitive(v) => v.$name_multi(),
797 value => Err(CastValueError {
798 requested: stringify!($name_multi),
799 got: value.value_type(),
800 }),
801 }
802 }
803 };
804}
805
806impl<I, P> Value<I, P> {
807 pub fn string(&self) -> Result<&str, CastValueError> {
819 match self {
820 Value::Primitive(v) => v.string(),
821 _ => Err(CastValueError {
822 requested: "string",
823 got: self.value_type(),
824 }),
825 }
826 }
827
828 pub fn strings(&self) -> Result<&[String], CastValueError> {
838 match self {
839 Value::Primitive(v) => v.strings(),
840 _ => Err(CastValueError {
841 requested: "strings",
842 got: self.value_type(),
843 }),
844 }
845 }
846
847 impl_primitive_getters!(tag, tags, Tags, Tag);
848 impl_primitive_getters!(date, dates, Date, DicomDate);
849 impl_primitive_getters!(time, times, Time, DicomTime);
850 impl_primitive_getters!(datetime, datetimes, DateTime, DicomDateTime);
851 impl_primitive_getters!(uint8, uint8_slice, U8, u8);
852 impl_primitive_getters!(uint16, uint16_slice, U16, u16);
853 impl_primitive_getters!(int16, int16_slice, I16, i16);
854 impl_primitive_getters!(uint32, uint32_slice, U32, u32);
855 impl_primitive_getters!(int32, int32_slice, I32, i32);
856 impl_primitive_getters!(int64, int64_slice, I64, i64);
857 impl_primitive_getters!(uint64, uint64_slice, U64, u64);
858 impl_primitive_getters!(float32, float32_slice, F32, f32);
859 impl_primitive_getters!(float64, float64_slice, F64, f64);
860}
861
862impl<I, P> From<PrimitiveValue> for Value<I, P> {
863 fn from(v: PrimitiveValue) -> Self {
864 Value::Primitive(v)
865 }
866}
867
868#[derive(Debug, Clone)]
870pub struct DataSetSequence<I> {
871 items: C<I>,
873 length: Length,
879}
880
881impl<I> DataSetSequence<I> {
882 #[inline]
891 pub fn new(items: impl Into<C<I>>, length: Length) -> Self {
892 DataSetSequence {
893 items: items.into(),
894 length,
895 }
896 }
897
898 #[inline]
901 pub fn empty() -> Self {
902 DataSetSequence {
903 items: Default::default(),
904 length: Length(0),
905 }
906 }
907
908 #[inline]
910 pub fn items(&self) -> &[I] {
911 &self.items
912 }
913
914 #[inline]
916 pub fn items_mut(&mut self) -> &mut C<I> {
917 &mut self.items
918 }
919
920 #[inline]
922 pub fn multiplicity(&self) -> u32 {
923 self.items.len() as u32
924 }
925
926 #[inline]
929 pub fn into_items(self) -> C<I> {
930 self.items
931 }
932
933 #[inline]
939 pub fn length(&self) -> Length {
940 HasLength::length(self)
941 }
942
943 #[inline]
946 pub fn truncate(&mut self, limit: usize) {
947 self.items.truncate(limit);
948 }
949}
950
951impl<I> HasLength for DataSetSequence<I> {
952 #[inline]
953 fn length(&self) -> Length {
954 self.length
955 }
956}
957
958impl<I> DicomValueType for DataSetSequence<I> {
959 #[inline]
960 fn value_type(&self) -> ValueType {
961 ValueType::DataSetSequence
962 }
963
964 #[inline]
965 fn cardinality(&self) -> usize {
966 self.items.len()
967 }
968}
969
970impl<I> From<Vec<I>> for DataSetSequence<I> {
971 #[inline]
974 fn from(items: Vec<I>) -> Self {
975 DataSetSequence {
976 items: items.into(),
977 length: Length::UNDEFINED,
978 }
979 }
980}
981
982impl<A, I> From<SmallVec<A>> for DataSetSequence<I>
983where
984 A: smallvec::Array<Item = I>,
985 C<I>: From<SmallVec<A>>,
986{
987 #[inline]
990 fn from(items: SmallVec<A>) -> Self {
991 DataSetSequence {
992 items: items.into(),
993 length: Length::UNDEFINED,
994 }
995 }
996}
997
998impl<I> From<[I; 1]> for DataSetSequence<I> {
999 #[inline]
1002 fn from([item]: [I; 1]) -> Self {
1003 DataSetSequence {
1004 items: smallvec::smallvec![item],
1005 length: Length::UNDEFINED,
1006 }
1007 }
1008}
1009
1010impl<I, P> From<DataSetSequence<I>> for Value<I, P> {
1011 #[inline]
1012 fn from(value: DataSetSequence<I>) -> Self {
1013 Value::Sequence(value)
1014 }
1015}
1016
1017impl<I> PartialEq<DataSetSequence<I>> for DataSetSequence<I>
1018where
1019 I: PartialEq,
1020{
1021 #[inline]
1027 fn eq(&self, other: &DataSetSequence<I>) -> bool {
1028 self.items() == other.items()
1029 }
1030}
1031
1032#[derive(Debug, Clone, PartialEq)]
1040pub struct PixelFragmentSequence<P> {
1041 offset_table: C<u32>,
1043 fragments: C<P>,
1045}
1046
1047impl<P> PixelFragmentSequence<P> {
1048 #[inline]
1054 pub fn new(offset_table: impl Into<C<u32>>, fragments: impl Into<C<P>>) -> Self {
1055 PixelFragmentSequence {
1056 offset_table: offset_table.into(),
1057 fragments: fragments.into(),
1058 }
1059 }
1060
1061 #[inline]
1065 pub fn new_fragments(fragments: impl Into<C<P>>) -> Self {
1066 PixelFragmentSequence {
1067 offset_table: Default::default(),
1068 fragments: fragments.into(),
1069 }
1070 }
1071
1072 #[inline]
1076 pub fn fragments(&self) -> &[P] {
1077 &self.fragments
1078 }
1079
1080 #[inline]
1084 pub fn fragments_mut(&mut self) -> &mut C<P> {
1085 &mut self.fragments
1086 }
1087
1088 #[inline]
1093 pub fn into_fragments(self) -> C<P> {
1094 self.fragments
1095 }
1096
1097 pub fn into_parts(self) -> (C<u32>, C<P>) {
1100 (self.offset_table, self.fragments)
1101 }
1102
1103 pub fn offset_table(&self) -> &[u32] {
1105 &self.offset_table
1106 }
1107
1108 pub fn offset_table_mut(&mut self) -> &mut C<u32> {
1110 &mut self.offset_table
1111 }
1112
1113 #[inline]
1119 pub fn length(&self) -> Length {
1120 HasLength::length(self)
1121 }
1122
1123 #[inline]
1128 pub fn truncate(&mut self, limit: usize) {
1129 self.fragments.truncate(limit);
1130 }
1131}
1132
1133impl<T, F, P> From<(T, F)> for PixelFragmentSequence<P>
1134where
1135 T: Into<C<u32>>,
1136 F: Into<C<P>>,
1137{
1138 fn from((offset_table, fragments): (T, F)) -> Self {
1145 PixelFragmentSequence::new(offset_table, fragments)
1146 }
1147}
1148
1149impl<I, P> From<PixelFragmentSequence<P>> for Value<I, P> {
1150 #[inline]
1151 fn from(value: PixelFragmentSequence<P>) -> Self {
1152 Value::PixelSequence(value)
1153 }
1154}
1155
1156impl<P> HasLength for PixelFragmentSequence<P> {
1157 #[inline]
1161 fn length(&self) -> Length {
1162 Length::UNDEFINED
1163 }
1164}
1165
1166impl<P> DicomValueType for PixelFragmentSequence<P> {
1167 #[inline]
1168 fn value_type(&self) -> ValueType {
1169 ValueType::PixelSequence
1170 }
1171
1172 #[inline]
1173 fn cardinality(&self) -> usize {
1174 1
1175 }
1176}
1177
1178#[cfg(test)]
1179mod tests {
1180 use super::*;
1181 use crate::dicom_value;
1182 use smallvec::smallvec;
1183
1184 #[test]
1185 fn to_int() {
1186 let value = Value::new(dicom_value!(I32, [1, 2, 5]));
1187 assert_eq!(value.to_int::<u32>().unwrap(), 1);
1188 assert_eq!(value.to_int::<i32>().unwrap(), 1);
1189 assert_eq!(value.to_int::<u16>().unwrap(), 1);
1190 assert_eq!(value.to_int::<i16>().unwrap(), 1);
1191 assert_eq!(value.to_int::<u64>().unwrap(), 1);
1192 assert_eq!(value.to_int::<i64>().unwrap(), 1);
1193
1194 assert_eq!(value.to_multi_int::<i32>().unwrap(), vec![1, 2, 5]);
1195 assert_eq!(value.to_multi_int::<u32>().unwrap(), vec![1, 2, 5]);
1196
1197 let value = Value::<EmptyObject, _>::new_sequence(smallvec![], Length::UNDEFINED);
1199
1200 assert!(matches!(
1201 value.to_int::<u32>(),
1202 Err(ConvertValueError {
1203 requested: "integer",
1204 original: ValueType::DataSetSequence,
1205 ..
1206 })
1207 ));
1208 }
1209
1210 #[test]
1211 fn to_float() {
1212 let value = Value::new(dicom_value!(F64, [1., 2., 5.]));
1213 assert_eq!(value.to_float32().unwrap(), 1.);
1214 assert_eq!(value.to_float64().unwrap(), 1.);
1215
1216 assert_eq!(value.to_multi_float32().unwrap(), vec![1., 2., 5.]);
1217 assert_eq!(value.to_multi_float64().unwrap(), vec![1., 2., 5.]);
1218
1219 let value = Value::<EmptyObject, _>::new_sequence(smallvec![], Length::UNDEFINED);
1221
1222 assert!(matches!(
1223 value.to_float32(),
1224 Err(ConvertValueError {
1225 requested: "float32",
1226 original: ValueType::DataSetSequence,
1227 ..
1228 })
1229 ));
1230 }
1231
1232 #[test]
1233 fn to_date() {
1234 let expected_dates = [
1235 DicomDate::from_ymd(2021, 2, 3).unwrap(),
1236 DicomDate::from_ymd(2022, 3, 4).unwrap(),
1237 DicomDate::from_ymd(2023, 4, 5).unwrap(),
1238 ];
1239
1240 let value = Value::new(dicom_value!(Strs, ["20210203", "20220304", "20230405"]));
1241 assert_eq!(value.to_date().unwrap(), expected_dates[0],);
1242 assert_eq!(value.to_multi_date().unwrap(), &expected_dates[..]);
1243
1244 let value_pair = Value::new(dicom_value!(
1245 Date,
1246 [
1247 DicomDate::from_ymd(2021, 2, 3).unwrap(),
1248 DicomDate::from_ymd(2022, 3, 4).unwrap(),
1249 ]
1250 ));
1251
1252 assert_eq!(value_pair.to_date().unwrap(), expected_dates[0]);
1253 assert_eq!(value_pair.to_multi_date().unwrap(), &expected_dates[0..2]);
1254
1255 assert!(matches!(
1257 value_pair.to_multi_int::<i64>(),
1258 Err(ConvertValueError {
1259 requested: "integer",
1260 original: ValueType::Date,
1261 ..
1262 })
1263 ));
1264
1265 let range_value = Value::new(dicom_value!(Str, "20210203-20220304"));
1266
1267 assert_eq!(
1269 range_value.to_date_range().unwrap(),
1270 DateRange::from_start_to_end(
1271 expected_dates[0].to_naive_date().unwrap(),
1272 expected_dates[1].to_naive_date().unwrap()
1273 )
1274 .unwrap()
1275 );
1276 }
1277
1278 #[test]
1279 fn getters() {
1280 assert_eq!(
1281 Value::new(dicom_value!(Strs, ["Smith^John"]))
1282 .string()
1283 .unwrap(),
1284 "Smith^John"
1285 );
1286
1287 assert_eq!(
1288 Value::new(dicom_value!(Strs, ["Smith^John"]))
1289 .strings()
1290 .unwrap(),
1291 &["Smith^John"]
1292 );
1293
1294 assert_eq!(Value::new(dicom_value!(I32, [1, 2, 5])).int32().unwrap(), 1,);
1295
1296 assert_eq!(
1297 Value::new(dicom_value!(I32, [1, 2, 5]))
1298 .int32_slice()
1299 .unwrap(),
1300 &[1, 2, 5],
1301 );
1302
1303 assert!(matches!(
1304 Value::new(dicom_value!(I32, [1, 2, 5])).uint32(),
1305 Err(CastValueError {
1306 requested: "uint32",
1307 got: ValueType::I32,
1308 ..
1309 })
1310 ));
1311
1312 assert!(matches!(
1313 Value::new(dicom_value!(I32, [1, 2, 5])).strings(),
1314 Err(CastValueError {
1315 requested: "strings",
1316 got: ValueType::I32,
1317 ..
1318 })
1319 ));
1320
1321 assert_eq!(
1322 Value::new(PrimitiveValue::Date(smallvec![DicomDate::from_ymd(
1323 2014, 10, 12
1324 )
1325 .unwrap()]))
1326 .date()
1327 .ok(),
1328 Some(DicomDate::from_ymd(2014, 10, 12).unwrap()),
1329 );
1330
1331 assert_eq!(
1332 Value::new(PrimitiveValue::Date(
1333 smallvec![DicomDate::from_ymd(2014, 10, 12).unwrap(); 5]
1334 ))
1335 .dates()
1336 .unwrap(),
1337 &[DicomDate::from_ymd(2014, 10, 12).unwrap(); 5]
1338 );
1339
1340 assert!(matches!(
1341 Value::new(PrimitiveValue::Date(smallvec![DicomDate::from_ymd(
1342 2014, 10, 12
1343 )
1344 .unwrap()]))
1345 .time(),
1346 Err(CastValueError {
1347 requested: "time",
1348 got: ValueType::Date,
1349 ..
1350 })
1351 ));
1352 }
1353
1354 #[derive(Debug, Clone, Copy, PartialEq)]
1355 struct DummyItem(u32);
1356
1357 impl HasLength for DummyItem {
1358 fn length(&self) -> Length {
1359 Length::defined(8)
1360 }
1361 }
1362
1363 #[test]
1364 fn value_eq() {
1365 let v1 = Value::<_, _>::from(PixelFragmentSequence::new(
1367 smallvec![],
1368 smallvec![vec![1, 2, 5]],
1369 ));
1370 let v2 = Value::new_pixel_sequence(smallvec![], smallvec![vec![1, 2, 5]]);
1371 assert_eq!(v1, v2);
1372 assert_eq!(v2, v1);
1373
1374 let v1 = Value::<DummyItem, _>::from(PixelFragmentSequence::new(
1376 smallvec![],
1377 smallvec![vec![1, 2, 5]],
1378 ));
1379
1380 let v3 = Value::from(PrimitiveValue::from("Something"));
1382 let v4 = Value::new(dicom_value!(Str, "Something"));
1383 let v3_2: Value = "Something".into();
1384 assert_eq!(v3, v4);
1385 assert_eq!(v3, v3_2);
1386
1387 let v3: Value<DummyItem, _> = PrimitiveValue::from("Something").into();
1389
1390 let v5 = Value::from(DataSetSequence::new(
1391 vec![DummyItem(0), DummyItem(1), DummyItem(2)],
1392 Length::defined(1000),
1393 ));
1394 let v6 = Value::from(DataSetSequence::new(
1395 vec![DummyItem(0), DummyItem(1), DummyItem(2)],
1396 Length::UNDEFINED,
1397 ));
1398 assert_eq!(v5, v6);
1399
1400 assert_ne!(v1, v3);
1401 assert_ne!(v3, v1);
1402 assert_ne!(v1, v6);
1403 assert_ne!(v6, v1);
1404 assert_ne!(v3, v6);
1405 assert_ne!(v6, v3);
1406 }
1407
1408 #[test]
1409 fn data_set_sequences() {
1410 let v = DataSetSequence::new(
1411 vec![DummyItem(1), DummyItem(2), DummyItem(5)],
1412 Length::defined(24),
1413 );
1414
1415 assert_eq!(v.cardinality(), 3);
1416 assert_eq!(v.value_type(), ValueType::DataSetSequence);
1417 assert_eq!(v.items(), &[DummyItem(1), DummyItem(2), DummyItem(5)]);
1418 assert_eq!(v.length(), Length(24));
1419
1420 let v = Value::<_, [u8; 0]>::from(v);
1421 assert_eq!(v.value_type(), ValueType::DataSetSequence);
1422 assert_eq!(v.cardinality(), 3);
1423 assert_eq!(
1424 v.items(),
1425 Some(&[DummyItem(1), DummyItem(2), DummyItem(5)][..])
1426 );
1427 assert_eq!(v.primitive(), None);
1428 assert_eq!(v.fragments(), None);
1429 assert_eq!(v.offset_table(), None);
1430 assert_eq!(v.length(), Length(24));
1431
1432 assert!(matches!(
1434 v.to_str(),
1435 Err(ConvertValueError {
1436 original: ValueType::DataSetSequence,
1437 ..
1438 })
1439 ));
1440 assert!(matches!(
1442 v.to_bytes(),
1443 Err(ConvertValueError {
1444 requested: "bytes",
1445 original: ValueType::DataSetSequence,
1446 ..
1447 })
1448 ));
1449
1450 let items = v.into_items().unwrap();
1452 assert_eq!(&items[..], &[DummyItem(1), DummyItem(2), DummyItem(5)][..]);
1453 }
1454
1455 #[test]
1456 fn pixel_fragment_sequences() {
1457 let v = PixelFragmentSequence::new(vec![], vec![vec![0x55; 128]]);
1458
1459 assert_eq!(v.cardinality(), 1);
1460 assert_eq!(v.value_type(), ValueType::PixelSequence);
1461 assert_eq!(v.fragments(), &[vec![0x55; 128]]);
1462 assert!(HasLength::length(&v).is_undefined());
1463
1464 let v = Value::<EmptyObject, _>::from(v);
1465 assert_eq!(v.cardinality(), 1);
1466 assert_eq!(v.value_type(), ValueType::PixelSequence);
1467 assert_eq!(v.items(), None);
1468 assert_eq!(v.primitive(), None);
1469 assert_eq!(v.fragments(), Some(&[vec![0x55; 128]][..]));
1470 assert_eq!(v.offset_table(), Some(&[][..]));
1471 assert!(HasLength::length(&v).is_undefined());
1472
1473 assert!(matches!(
1475 v.to_str(),
1476 Err(ConvertValueError {
1477 requested: "string",
1478 original: ValueType::PixelSequence,
1479 ..
1480 })
1481 ));
1482
1483 assert!(matches!(
1485 v.to_bytes(),
1486 Err(ConvertValueError {
1487 requested: "bytes",
1488 original: ValueType::PixelSequence,
1489 ..
1490 })
1491 ));
1492
1493 let fragments = v.into_fragments().unwrap();
1495 assert_eq!(&fragments[..], &[vec![0x55; 128]]);
1496 }
1497}