Skip to main content

ferroui_controls/
native_menu_item_base.rs

1use crate::NativeMenu;
2use ferroui_base::{
3    ferro_class, ferro_class_info, ferro_impl_classes, ferro_properties, DirectProperty, FerroObject, FerroObjectImpl,
4    FerroProperty, Ref, WeakRef,
5};
6use std::cell::RefCell;
7
8/// The base class of the items of a [`NativeMenu`].
9#[repr(C)]
10pub struct NativeMenuItemBase {
11    base: FerroObject,
12    /// The menu that holds the item. A back pointer: the menu owns its
13    /// items.
14    parent: RefCell<Option<WeakRef<NativeMenu>>>,
15}
16
17ferro_class!(NativeMenuItemBase: FerroObject);
18ferro_class_info!(NativeMenuItemBase {});
19ferro_impl_classes!(NativeMenuItemBase: FerroObjectImpl);
20
21ferro_properties! {
22    impl NativeMenuItemBase {
23        /// Defines the `Parent` property.
24        pub fn parent_property() -> DirectProperty<NativeMenuItemBase, Option<Ref<NativeMenu>>> {
25            FerroProperty::register_direct::<NativeMenuItemBase, _>("Parent", |o| o.parent(), None, None)
26        }
27    }
28}
29
30impl NativeMenuItemBase {
31    /// Creates the class data; see [`FerroObject::construct`]. For the
32    /// classes of this crate that derive from this one.
33    pub(crate) fn construct() -> Self {
34        Self { base: FerroObject::construct(), parent: RefCell::new(None) }
35    }
36
37    /// The menu that holds the item.
38    pub fn parent(&self) -> Option<Ref<NativeMenu>> {
39        let parent = self.parent.borrow().clone();
40        parent.and_then(|parent| parent.upgrade())
41    }
42
43    pub(crate) fn set_parent(&self, value: Option<Ref<NativeMenu>>) {
44        let old = self.parent();
45        if old == value {
46            return;
47        }
48        *self.parent.borrow_mut() = value.as_ref().map(|value| value.downgrade());
49        self.raise_direct_property_changed(Self::parent_property(), &old, &value);
50    }
51}