1use crate::error::FieldValueError;
7
8#[derive(Debug, Clone, PartialEq)]
49pub enum FieldValue {
50 Boolean(bool),
52 String(String),
54 Float(f32),
56
57 Vector2D([f32; 2]),
59 Vector3D([f32; 3]),
61 Vector4D([f32; 4]),
63
64 Signed8(i8),
66 Signed16(i16),
68 Signed32(i32),
70 Signed64(i64),
72
73 Unsigned8(u8),
75 Unsigned16(u16),
77 Unsigned32(u32),
79 Unsigned64(u64),
81}
82
83impl FieldValue {
84 pub fn type_name(&self) -> &'static str {
86 match self {
87 FieldValue::Boolean(_) => "Boolean",
88 FieldValue::String(_) => "String",
89 FieldValue::Float(_) => "Float",
90 FieldValue::Vector2D(_) => "Vector2D",
91 FieldValue::Vector3D(_) => "Vector3D",
92 FieldValue::Vector4D(_) => "Vector4D",
93 FieldValue::Signed8(_) => "Signed8",
94 FieldValue::Signed16(_) => "Signed16",
95 FieldValue::Signed32(_) => "Signed32",
96 FieldValue::Signed64(_) => "Signed64",
97 FieldValue::Unsigned8(_) => "Unsigned8",
98 FieldValue::Unsigned16(_) => "Unsigned16",
99 FieldValue::Unsigned32(_) => "Unsigned32",
100 FieldValue::Unsigned64(_) => "Unsigned64",
101 }
102 }
103}
104
105pub trait IntoFieldValue {
107 fn into_field_value(self) -> FieldValue;
109}
110
111pub trait FieldRewriteResult {
116 fn into_field_rewrite_result(self) -> Option<FieldValue>;
118}
119
120impl<T> FieldRewriteResult for T
121where
122 T: IntoFieldValue,
123{
124 fn into_field_rewrite_result(self) -> Option<FieldValue> {
125 Some(self.into_field_value())
126 }
127}
128
129impl<T> FieldRewriteResult for Option<T>
130where
131 T: IntoFieldValue,
132{
133 fn into_field_rewrite_result(self) -> Option<FieldValue> {
134 self.map(IntoFieldValue::into_field_value)
135 }
136}
137
138impl IntoFieldValue for FieldValue {
139 fn into_field_value(self) -> FieldValue {
140 self
141 }
142}
143
144impl IntoFieldValue for String {
145 fn into_field_value(self) -> FieldValue {
146 FieldValue::String(self)
147 }
148}
149
150impl IntoFieldValue for &str {
151 fn into_field_value(self) -> FieldValue {
152 FieldValue::String(self.to_string())
153 }
154}
155
156impl IntoFieldValue for bool {
157 fn into_field_value(self) -> FieldValue {
158 FieldValue::Boolean(self)
159 }
160}
161
162impl IntoFieldValue for f32 {
163 fn into_field_value(self) -> FieldValue {
164 FieldValue::Float(self)
165 }
166}
167
168impl IntoFieldValue for [f32; 2] {
169 fn into_field_value(self) -> FieldValue {
170 FieldValue::Vector2D(self)
171 }
172}
173
174impl IntoFieldValue for [f32; 3] {
175 fn into_field_value(self) -> FieldValue {
176 FieldValue::Vector3D(self)
177 }
178}
179
180impl IntoFieldValue for [f32; 4] {
181 fn into_field_value(self) -> FieldValue {
182 FieldValue::Vector4D(self)
183 }
184}
185
186macro_rules! impl_into_field_value {
187 ($($ty:ty => $variant:ident),* $(,)?) => {
188 $(
189 impl IntoFieldValue for $ty {
190 fn into_field_value(self) -> FieldValue {
191 FieldValue::$variant(self)
192 }
193 }
194 )*
195 };
196}
197
198impl_into_field_value! {
199 i8 => Signed8,
200 i16 => Signed16,
201 i32 => Signed32,
202 i64 => Signed64,
203 u8 => Unsigned8,
204 u16 => Unsigned16,
205 u32 => Unsigned32,
206 u64 => Unsigned64,
207}
208
209impl TryInto<String> for FieldValue {
210 type Error = FieldValueError;
211
212 fn try_into(self) -> Result<String, FieldValueError> {
213 if let FieldValue::String(x) = self {
214 Ok(x)
215 } else {
216 Err(FieldValueError::ConversionError(
217 format!("{:?}", self),
218 "String".to_string(),
219 ))
220 }
221 }
222}
223
224impl TryInto<String> for &FieldValue {
225 type Error = FieldValueError;
226
227 fn try_into(self) -> Result<String, FieldValueError> {
228 if let FieldValue::String(x) = self {
229 Ok(x.to_owned())
230 } else {
231 Err(FieldValueError::ConversionError(
232 format!("{:?}", self),
233 "String".to_string(),
234 ))
235 }
236 }
237}
238
239impl TryInto<[f32; 2]> for FieldValue {
240 type Error = FieldValueError;
241
242 fn try_into(self) -> Result<[f32; 2], FieldValueError> {
243 if let FieldValue::Vector2D(x) = self {
244 Ok(x)
245 } else {
246 Err(FieldValueError::ConversionError(
247 format!("{:?}", self),
248 "[f32; 2]".to_string(),
249 ))
250 }
251 }
252}
253
254impl TryInto<[f32; 2]> for &FieldValue {
255 type Error = FieldValueError;
256
257 fn try_into(self) -> Result<[f32; 2], FieldValueError> {
258 if let FieldValue::Vector2D(x) = self {
259 Ok(*x)
260 } else {
261 Err(FieldValueError::ConversionError(
262 format!("{:?}", self),
263 "[f32; 2]".to_string(),
264 ))
265 }
266 }
267}
268
269impl TryInto<(f32, f32)> for FieldValue {
270 type Error = FieldValueError;
271
272 fn try_into(self) -> Result<(f32, f32), FieldValueError> {
273 if let FieldValue::Vector2D(x) = self {
274 Ok(x.into())
275 } else {
276 Err(FieldValueError::ConversionError(
277 format!("{:?}", self),
278 "(f32, f32)".to_string(),
279 ))
280 }
281 }
282}
283
284impl TryInto<(f32, f32)> for &FieldValue {
285 type Error = FieldValueError;
286
287 fn try_into(self) -> Result<(f32, f32), FieldValueError> {
288 if let FieldValue::Vector2D(x) = self {
289 Ok((*x).into())
290 } else {
291 Err(FieldValueError::ConversionError(
292 format!("{:?}", self),
293 "(f32, f32)".to_string(),
294 ))
295 }
296 }
297}
298
299impl TryInto<[f32; 3]> for FieldValue {
300 type Error = FieldValueError;
301
302 fn try_into(self) -> Result<[f32; 3], FieldValueError> {
303 if let FieldValue::Vector3D(x) = self {
304 Ok(x)
305 } else {
306 Err(FieldValueError::ConversionError(
307 format!("{:?}", self),
308 "[f32; 3]".to_string(),
309 ))
310 }
311 }
312}
313
314impl TryInto<[f32; 3]> for &FieldValue {
315 type Error = FieldValueError;
316
317 fn try_into(self) -> Result<[f32; 3], FieldValueError> {
318 if let FieldValue::Vector3D(x) = self {
319 Ok(*x)
320 } else {
321 Err(FieldValueError::ConversionError(
322 format!("{:?}", self),
323 "[f32; 3]".to_string(),
324 ))
325 }
326 }
327}
328
329impl TryInto<(f32, f32, f32)> for FieldValue {
330 type Error = FieldValueError;
331
332 fn try_into(self) -> Result<(f32, f32, f32), FieldValueError> {
333 if let FieldValue::Vector3D(x) = self {
334 Ok(x.into())
335 } else {
336 Err(FieldValueError::ConversionError(
337 format!("{:?}", self),
338 "(f32, f32, f32)".to_string(),
339 ))
340 }
341 }
342}
343
344impl TryInto<(f32, f32, f32)> for &FieldValue {
345 type Error = FieldValueError;
346
347 fn try_into(self) -> Result<(f32, f32, f32), FieldValueError> {
348 if let FieldValue::Vector3D(x) = self {
349 Ok((*x).into())
350 } else {
351 Err(FieldValueError::ConversionError(
352 format!("{:?}", self),
353 "(f32, f32, f32)".to_string(),
354 ))
355 }
356 }
357}
358
359impl TryInto<[f32; 4]> for FieldValue {
360 type Error = FieldValueError;
361
362 fn try_into(self) -> Result<[f32; 4], FieldValueError> {
363 if let FieldValue::Vector4D(x) = self {
364 Ok(x)
365 } else {
366 Err(FieldValueError::ConversionError(
367 format!("{:?}", self),
368 "[f32; 4]".to_string(),
369 ))
370 }
371 }
372}
373
374impl TryInto<[f32; 4]> for &FieldValue {
375 type Error = FieldValueError;
376
377 fn try_into(self) -> Result<[f32; 4], FieldValueError> {
378 if let FieldValue::Vector4D(x) = self {
379 Ok(*x)
380 } else {
381 Err(FieldValueError::ConversionError(
382 format!("{:?}", self),
383 "[f32; 4]".to_string(),
384 ))
385 }
386 }
387}
388
389impl TryInto<(f32, f32, f32, f32)> for FieldValue {
390 type Error = FieldValueError;
391
392 fn try_into(self) -> Result<(f32, f32, f32, f32), FieldValueError> {
393 if let FieldValue::Vector4D(x) = self {
394 Ok(x.into())
395 } else {
396 Err(FieldValueError::ConversionError(
397 format!("{:?}", self),
398 "(f32, f32, f32, f32)".to_string(),
399 ))
400 }
401 }
402}
403
404impl TryInto<(f32, f32, f32, f32)> for &FieldValue {
405 type Error = FieldValueError;
406
407 fn try_into(self) -> Result<(f32, f32, f32, f32), FieldValueError> {
408 if let FieldValue::Vector4D(x) = self {
409 Ok((*x).into())
410 } else {
411 Err(FieldValueError::ConversionError(
412 format!("{:?}", self),
413 "(f32, f32, f32, f32)".to_string(),
414 ))
415 }
416 }
417}
418
419impl TryInto<Vec<f32>> for FieldValue {
420 type Error = FieldValueError;
421
422 fn try_into(self) -> Result<Vec<f32>, FieldValueError> {
423 match self {
424 FieldValue::Vector2D(x) => Ok(x.to_vec()),
425 FieldValue::Vector3D(x) => Ok(x.to_vec()),
426 FieldValue::Vector4D(x) => Ok(x.to_vec()),
427 _ => Err(FieldValueError::ConversionError(
428 format!("{:?}", self),
429 "Vec<f32>".to_string(),
430 )),
431 }
432 }
433}
434
435impl TryInto<Vec<f32>> for &FieldValue {
436 type Error = FieldValueError;
437
438 fn try_into(self) -> Result<Vec<f32>, FieldValueError> {
439 match self {
440 FieldValue::Vector2D(x) => Ok(x.to_vec()),
441 FieldValue::Vector3D(x) => Ok(x.to_vec()),
442 FieldValue::Vector4D(x) => Ok(x.to_vec()),
443 _ => Err(FieldValueError::ConversionError(
444 format!("{:?}", self),
445 "Vec<f32>".to_string(),
446 )),
447 }
448 }
449}
450
451impl TryInto<f32> for FieldValue {
452 type Error = FieldValueError;
453
454 fn try_into(self) -> Result<f32, FieldValueError> {
455 if let FieldValue::Float(x) = self {
456 Ok(x)
457 } else {
458 Err(FieldValueError::ConversionError(
459 format!("{:?}", self),
460 "f32".to_string(),
461 ))
462 }
463 }
464}
465
466impl TryInto<f32> for &FieldValue {
467 type Error = FieldValueError;
468
469 fn try_into(self) -> Result<f32, FieldValueError> {
470 if let FieldValue::Float(x) = self {
471 Ok(*x)
472 } else {
473 Err(FieldValueError::ConversionError(
474 format!("{:?}", self),
475 "f32".to_string(),
476 ))
477 }
478 }
479}
480
481impl TryInto<bool> for FieldValue {
482 type Error = FieldValueError;
483
484 fn try_into(self) -> Result<bool, FieldValueError> {
485 if let FieldValue::Boolean(x) = self {
486 Ok(x)
487 } else {
488 Err(FieldValueError::ConversionError(
489 format!("{:?}", self),
490 "bool".to_string(),
491 ))
492 }
493 }
494}
495
496impl TryInto<bool> for &FieldValue {
497 type Error = FieldValueError;
498
499 fn try_into(self) -> Result<bool, FieldValueError> {
500 if let FieldValue::Boolean(x) = self {
501 Ok(*x)
502 } else {
503 Err(FieldValueError::ConversionError(
504 format!("{:?}", self),
505 "bool".to_string(),
506 ))
507 }
508 }
509}
510
511macro_rules! impl_try_into_for_integers {
512 ($target:ty) => {
513 impl TryInto<$target> for FieldValue {
514 type Error = FieldValueError;
515
516 fn try_into(self) -> Result<$target, FieldValueError> {
517 match self {
518 FieldValue::Signed8(x) => {
520 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
521 FieldValueError::ConversionError(
522 format!("{:?}", x),
523 stringify!($target).to_string(),
524 )
525 })?)
526 }
527 FieldValue::Signed16(x) => {
528 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
529 FieldValueError::ConversionError(
530 format!("{:?}", x),
531 stringify!($target).to_string(),
532 )
533 })?)
534 }
535 FieldValue::Signed32(x) => {
536 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
537 FieldValueError::ConversionError(
538 format!("{:?}", x),
539 stringify!($target).to_string(),
540 )
541 })?)
542 }
543 FieldValue::Signed64(x) => {
544 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
545 FieldValueError::ConversionError(
546 format!("{:?}", x),
547 stringify!($target).to_string(),
548 )
549 })?)
550 }
551 FieldValue::Unsigned8(x) => {
552 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
553 FieldValueError::ConversionError(
554 format!("{:?}", x),
555 stringify!($target).to_string(),
556 )
557 })?)
558 }
559 FieldValue::Unsigned16(x) => {
560 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
561 FieldValueError::ConversionError(
562 format!("{:?}", x),
563 stringify!($target).to_string(),
564 )
565 })?)
566 }
567 FieldValue::Unsigned32(x) => {
568 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
569 FieldValueError::ConversionError(
570 format!("{:?}", x),
571 stringify!($target).to_string(),
572 )
573 })?)
574 }
575 FieldValue::Unsigned64(x) => {
576 Ok(TryInto::<$target>::try_into(x).map_err(|_| {
577 FieldValueError::ConversionError(
578 format!("{:?}", x),
579 stringify!($target).to_string(),
580 )
581 })?)
582 }
583 FieldValue::Float(x) => Ok(x as $target),
584 _ => Err(FieldValueError::ConversionError(
585 format!("{:?}", self),
586 stringify!($target).to_string(),
587 )),
588 }
589 }
590 }
591
592 impl TryInto<$target> for &FieldValue {
593 type Error = FieldValueError;
594
595 fn try_into(self) -> Result<$target, FieldValueError> {
596 match self {
597 FieldValue::Signed8(x) => {
599 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
600 FieldValueError::ConversionError(
601 format!("{:?}", x),
602 stringify!($target).to_string(),
603 )
604 })?)
605 }
606 FieldValue::Signed16(x) => {
607 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
608 FieldValueError::ConversionError(
609 format!("{:?}", x),
610 stringify!($target).to_string(),
611 )
612 })?)
613 }
614 FieldValue::Signed32(x) => {
615 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
616 FieldValueError::ConversionError(
617 format!("{:?}", x),
618 stringify!($target).to_string(),
619 )
620 })?)
621 }
622 FieldValue::Signed64(x) => {
623 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
624 FieldValueError::ConversionError(
625 format!("{:?}", x),
626 stringify!($target).to_string(),
627 )
628 })?)
629 }
630 FieldValue::Unsigned8(x) => {
631 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
632 FieldValueError::ConversionError(
633 format!("{:?}", x),
634 stringify!($target).to_string(),
635 )
636 })?)
637 }
638 FieldValue::Unsigned16(x) => {
639 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
640 FieldValueError::ConversionError(
641 format!("{:?}", x),
642 stringify!($target).to_string(),
643 )
644 })?)
645 }
646 FieldValue::Unsigned32(x) => {
647 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
648 FieldValueError::ConversionError(
649 format!("{:?}", x),
650 stringify!($target).to_string(),
651 )
652 })?)
653 }
654 FieldValue::Unsigned64(x) => {
655 Ok(TryInto::<$target>::try_into(*x).map_err(|_| {
656 FieldValueError::ConversionError(
657 format!("{:?}", x),
658 stringify!($target).to_string(),
659 )
660 })?)
661 }
662 FieldValue::Float(x) => Ok(*x as $target),
663 _ => Err(FieldValueError::ConversionError(
664 format!("{:?}", self),
665 stringify!($target).to_string(),
666 )),
667 }
668 }
669 }
670 };
671}
672
673impl_try_into_for_integers!(i8);
674impl_try_into_for_integers!(i16);
675impl_try_into_for_integers!(i32);
676impl_try_into_for_integers!(i64);
677impl_try_into_for_integers!(i128);
678impl_try_into_for_integers!(u8);
679impl_try_into_for_integers!(u16);
680impl_try_into_for_integers!(u32);
681impl_try_into_for_integers!(u64);
682impl_try_into_for_integers!(u128);
683impl_try_into_for_integers!(usize);
684impl_try_into_for_integers!(isize);
685
686#[allow(dead_code)]
687impl FieldValue {
688 #[inline]
690 pub fn string(&self) -> String {
691 if let FieldValue::String(s) = self {
692 s.to_string()
693 } else {
694 panic!("Tried to read as String, Found {:?}", self);
695 }
696 }
697
698 #[inline]
700 pub fn bool(&self) -> bool {
701 if let FieldValue::Boolean(b) = self {
702 *b
703 } else {
704 panic!("Tried to read as Boolean, Found {:?}", self);
705 }
706 }
707
708 #[inline]
710 pub fn f32(&self) -> f32 {
711 if let FieldValue::Float(f) = self {
712 *f
713 } else {
714 panic!("Tried to read as Float, Found {:?}", self);
715 }
716 }
717
718 #[inline]
721 pub fn vec2(&self) -> &[f32; 2] {
722 if let FieldValue::Vector2D(v) = self {
723 v
724 } else {
725 panic!("Tried to read as Vector2D, Found {:?}", self);
726 }
727 }
728
729 #[inline]
732 pub fn vec3(&self) -> &[f32; 3] {
733 if let FieldValue::Vector3D(v) = self {
734 v
735 } else {
736 panic!("Tried to read as Vector3D, Found {:?}", self);
737 }
738 }
739
740 #[inline]
743 pub fn vec4(&self) -> &[f32; 4] {
744 if let FieldValue::Vector4D(v) = self {
745 v
746 } else {
747 panic!("Tried to read as Vector4D, Found {:?}", self);
748 }
749 }
750
751 #[inline]
753 pub fn i8(&self) -> i8 {
754 match self {
755 FieldValue::Signed8(x) => *x,
756 _ => panic!("Tried to read as i8, Found {:?}", self),
757 }
758 }
759
760 #[inline]
762 pub fn i16(&self) -> i16 {
763 match self {
764 FieldValue::Signed16(x) => *x,
765 _ => panic!("Tried to read as i16, Found {:?}", self),
766 }
767 }
768
769 #[inline]
771 pub fn i32(&self) -> i32 {
772 match self {
773 FieldValue::Signed32(x) => *x,
774 _ => panic!("Tried to read as i32, Found {:?}", self),
775 }
776 }
777
778 #[inline]
780 pub fn i64(&self) -> i64 {
781 match self {
782 FieldValue::Signed64(x) => *x,
783 _ => panic!("Tried to read as i64, Found {:?}", self),
784 }
785 }
786
787 #[inline]
789 pub fn u8(&self) -> u8 {
790 match self {
791 FieldValue::Unsigned8(x) => *x,
792 _ => panic!("Tried to read as u8, Found {:?}", self),
793 }
794 }
795
796 #[inline]
798 pub fn u16(&self) -> u16 {
799 match self {
800 FieldValue::Unsigned16(x) => *x,
801 _ => panic!("Tried to read as u16, Found {:?}", self),
802 }
803 }
804
805 #[inline]
807 pub fn u32(&self) -> u32 {
808 match self {
809 FieldValue::Unsigned32(x) => *x,
810 _ => panic!("Tried to read as u32, Found {:?}", self),
811 }
812 }
813
814 #[inline]
816 pub fn u64(&self) -> u64 {
817 match self {
818 FieldValue::Unsigned64(x) => *x,
819 _ => panic!("Tried to read as u64, Found {:?}", self),
820 }
821 }
822
823 #[inline]
826 pub fn usize(&self) -> usize {
827 match self {
828 FieldValue::Unsigned32(x) => *x as usize,
829 FieldValue::Unsigned64(x) => *x as usize,
830 _ => panic!("Tried to read as usize, Found {:?}", self),
831 }
832 }
833}