Skip to main content

icu_capi/
calendar.rs

1// This file is part of ICU4X. For terms of use, please see the file
2// called LICENSE at the top level of the ICU4X source tree
3// (online at: https://github.com/unicode-org/icu4x/blob/main/LICENSE ).
4
5#[diplomat::bridge]
6#[diplomat::abi_rename = "icu4x_{0}_mv1"]
7pub mod ffi {
8    use alloc::boxed::Box;
9    use alloc::sync::Arc;
10
11    #[cfg(feature = "buffer_provider")]
12    use crate::unstable::errors::ffi::DataError;
13    use crate::unstable::locale_core::ffi::Locale;
14    #[cfg(feature = "buffer_provider")]
15    use crate::unstable::provider::ffi::DataProvider;
16
17    /// The various calendar types currently supported by [`Calendar`]
18    #[diplomat::enum_convert(icu_calendar::AnyCalendarKind, needs_wildcard)]
19    #[diplomat::rust_link(icu::calendar::AnyCalendarKind, Enum)]
20    #[non_exhaustive]
21    pub enum CalendarKind {
22        /// The kind of an Iso calendar
23        // AnyCalendarKind in Rust doesn't have a default, but it is useful to have one
24        // here for consistent behavior.
25        #[diplomat::attr(auto, default)]
26        Iso = 0,
27        /// The kind of a Gregorian calendar
28        Gregorian = 1,
29        /// The kind of a Buddhist calendar
30        Buddhist = 2,
31        /// The kind of a Japanese calendar with modern eras
32        Japanese = 3,
33        /// The kind of a Japanese calendar with modern and historic eras
34        JapaneseExtended = 4,
35        /// The kind of an Ethiopian calendar, with Amete Mihret era
36        Ethiopian = 5,
37        /// The kind of an Ethiopian calendar, with Amete Alem era
38        EthiopianAmeteAlem = 6,
39        /// The kind of a Indian calendar
40        Indian = 7,
41        /// The kind of a Coptic calendar
42        Coptic = 8,
43        /// The kind of a Dangi calendar
44        Dangi = 9,
45        /// The kind of a Chinese calendar
46        Chinese = 10,
47        /// The kind of a Hebrew calendar
48        Hebrew = 11,
49        /// The kind of a Hijri tabular, type II leap years, Friday epoch, calendar
50        HijriTabularTypeIIFriday = 12,
51        /// The kind of a Hijri simulated, Mecca calendar
52        HijriSimulatedMecca = 18,
53        /// The kind of a Hijri tabular, type II leap years, Thursday epoch, calendar
54        HijriTabularTypeIIThursday = 14,
55        /// The kind of a Hijri Umm al-Qura calendar
56        HijriUmmAlQura = 15,
57        /// The kind of a Persian calendar
58        Persian = 16,
59        /// The kind of a Roc calendar
60        Roc = 17,
61    }
62
63    impl CalendarKind {
64        /// Creates a new [`CalendarKind`] for the specified locale, using compiled data.
65        #[diplomat::rust_link(icu::calendar::AnyCalendarKind::new, FnInEnum)]
66        pub fn create(locale: &Locale) -> Self {
67            let prefs = (&locale.0).into();
68            icu_calendar::AnyCalendarKind::new(prefs).into()
69        }
70    }
71
72    #[diplomat::opaque]
73    #[diplomat::transparent_convert]
74    #[diplomat::rust_link(icu::calendar::AnyCalendar, Enum)]
75    pub struct Calendar(pub Arc<icu_calendar::AnyCalendar>);
76
77    impl Calendar {
78        /// Creates a new [`Calendar`] for the specified kind, using compiled data.
79        #[diplomat::rust_link(icu::calendar::AnyCalendar::new, FnInEnum)]
80        #[diplomat::attr(auto, constructor)]
81        #[cfg(feature = "compiled_data")]
82        pub fn create(kind: CalendarKind) -> Box<Calendar> {
83            Box::new(Calendar(Arc::new(icu_calendar::AnyCalendar::new(
84                kind.into(),
85            ))))
86        }
87
88        /// Creates a new [`Calendar`] for the specified kind, using a particular data source.
89        #[diplomat::rust_link(icu::calendar::AnyCalendar::new, FnInEnum)]
90        #[diplomat::attr(all(supports = fallible_constructors, supports = named_constructors), named_constructor = "new_with_provider")]
91        #[cfg(feature = "buffer_provider")]
92        pub fn create_with_provider(
93            provider: &DataProvider,
94            kind: CalendarKind,
95        ) -> Result<Box<Calendar>, DataError> {
96            Ok(Box::new(Calendar(Arc::new(
97                icu_calendar::AnyCalendar::try_new_with_buffer_provider(
98                    provider.get()?,
99                    kind.into(),
100                )?,
101            ))))
102        }
103
104        /// Returns the kind of this calendar
105        #[diplomat::rust_link(icu::calendar::AnyCalendar::kind, FnInEnum)]
106        #[diplomat::attr(auto, getter)]
107        #[diplomat::attr(demo_gen, disable)] // this just returns the single constructor argument
108        pub fn kind(&self) -> CalendarKind {
109            self.0.kind().into()
110        }
111    }
112}