objc2-gameplay-kit 0.3.2

Bindings to the GameplayKit framework
Documentation
//! This file has been automatically generated by `objc2`'s `header-translator`.
//! DO NOT EDIT
use core::ffi::*;
use core::ptr::NonNull;
use objc2::__framework_prelude::*;
use objc2_foundation::*;

use crate::*;

extern_class!(
    /// A component is the data and logic for one part of an object in an entity-component system.
    /// Entities have many components but components are associated with only a single entity.
    ///
    /// Components across entities are best arranged in ComponentSystems, which are homogeneous
    /// collections of components that the game logic updates in a deterministic order.
    ///
    ///
    /// See: GKComponentSystem
    ///
    /// See also [Apple's documentation](https://developer.apple.com/documentation/gameplaykit/gkcomponent?language=objc)
    #[unsafe(super(NSObject))]
    #[derive(Debug, PartialEq, Eq, Hash)]
    pub struct GKComponent;
);

extern_conformance!(
    unsafe impl NSCoding for GKComponent {}
);

extern_conformance!(
    unsafe impl NSCopying for GKComponent {}
);

unsafe impl CopyingHelper for GKComponent {
    type Result = Self;
}

extern_conformance!(
    unsafe impl NSObjectProtocol for GKComponent {}
);

extern_conformance!(
    unsafe impl NSSecureCoding for GKComponent {}
);

impl GKComponent {
    extern_methods!(
        #[cfg(feature = "GKEntity")]
        /// The entity that this component belongs to. Defaults to nil until the component is added to an entity.
        #[unsafe(method(entity))]
        #[unsafe(method_family = none)]
        pub unsafe fn entity(&self) -> Option<Retained<GKEntity>>;

        /// Updates the component with the given delta time since the last update. Each component should
        /// perform its time-based logic in this method.
        #[unsafe(method(updateWithDeltaTime:))]
        #[unsafe(method_family = none)]
        pub unsafe fn updateWithDeltaTime(&self, seconds: NSTimeInterval);

        /// Override this to perform game logic when this component is added to an entity
        #[unsafe(method(didAddToEntity))]
        #[unsafe(method_family = none)]
        pub unsafe fn didAddToEntity(&self);

        /// Override this to perform game logic before this entity is removed from it's entity
        #[unsafe(method(willRemoveFromEntity))]
        #[unsafe(method_family = none)]
        pub unsafe fn willRemoveFromEntity(&self);
    );
}

/// Methods declared on superclass `NSObject`.
impl GKComponent {
    extern_methods!(
        #[unsafe(method(init))]
        #[unsafe(method_family = init)]
        pub unsafe fn init(this: Allocated<Self>) -> Retained<Self>;

        #[unsafe(method(new))]
        #[unsafe(method_family = new)]
        pub unsafe fn new() -> Retained<Self>;
    );
}

extern_class!(
    /// A component system is a homogeneous collection of components that are intended to be called at the same time.
    /// The system is homogeneous, meaning it only allows members of the same class into the system.
    ///
    /// See also [Apple's documentation](https://developer.apple.com/documentation/gameplaykit/gkcomponentsystem?language=objc)
    #[unsafe(super(NSObject))]
    #[derive(Debug, PartialEq, Eq, Hash)]
    pub struct GKComponentSystem<ComponentType: ?Sized = AnyObject>;
);

impl<ComponentType: ?Sized + Message + AsRef<GKComponent>> GKComponentSystem<ComponentType> {
    /// Unchecked conversion of the generic parameter.
    ///
    /// # Safety
    ///
    /// The generic must be valid to reinterpret as the given type.
    #[inline]
    pub unsafe fn cast_unchecked<NewComponentType: ?Sized + Message + AsRef<GKComponent>>(
        &self,
    ) -> &GKComponentSystem<NewComponentType> {
        unsafe { &*((self as *const Self).cast()) }
    }
}

extern_conformance!(
    unsafe impl<ComponentType: ?Sized + AsRef<GKComponent>> NSFastEnumeration
        for GKComponentSystem<ComponentType>
    {
    }
);

extern_conformance!(
    unsafe impl<ComponentType: ?Sized + AsRef<GKComponent>> NSObjectProtocol
        for GKComponentSystem<ComponentType>
    {
    }
);

impl<ComponentType: Message + AsRef<GKComponent>> GKComponentSystem<ComponentType> {
    extern_methods!(
        /// The collection's component class. Any selector the component supports can be called on the system and it will be forwarded
        /// to each of the components in the collection.
        #[unsafe(method(componentClass))]
        #[unsafe(method_family = none)]
        pub unsafe fn componentClass(&self) -> &'static AnyClass;

        /// The array of components currently in the system.
        #[unsafe(method(components))]
        #[unsafe(method_family = none)]
        pub unsafe fn components(&self) -> Retained<NSArray<ComponentType>>;

        /// Supports getting components via a [] subscript.
        #[unsafe(method(objectAtIndexedSubscript:))]
        #[unsafe(method_family = none)]
        pub unsafe fn objectAtIndexedSubscript(&self, idx: NSUInteger) -> Retained<ComponentType>;

        /// Initializes a system for the given component class. The receiver can now only accept components of the given class.
        ///
        /// # Safety
        ///
        /// `cls` probably has further requirements.
        #[unsafe(method(initWithComponentClass:))]
        #[unsafe(method_family = init)]
        pub unsafe fn initWithComponentClass(
            this: Allocated<Self>,
            cls: &AnyClass,
        ) -> Retained<Self>;

        /// Adds a component to the system. The component must be of the same class as the system's componentClass.
        /// The component is added to the tail of the collection and will be processed after components that were added before it.
        ///
        ///
        /// Throws a if the component added is not a kind of the system's componentClass.
        #[unsafe(method(addComponent:))]
        #[unsafe(method_family = none)]
        pub unsafe fn addComponent(&self, component: &ComponentType);

        #[cfg(feature = "GKEntity")]
        /// Adds the supported component from the entity's component collection.
        /// This is conceptually the same as the pseudo-code:
        ///
        /// for (GKComponent *component in entity.components)
        /// if (component.class == system.componentClass)
        /// [system addComponent:component]
        ///
        ///
        /// See: GKEntity.components
        #[unsafe(method(addComponentWithEntity:))]
        #[unsafe(method_family = none)]
        pub unsafe fn addComponentWithEntity(&self, entity: &GKEntity);

        #[cfg(feature = "GKEntity")]
        /// Removes the supported component from the entity's component collection
        /// This is conceptually the same as the pseudo-code:
        ///
        /// for (GKComponent *component in entity.components)
        /// if (component.class == system.componentClass)
        /// [system removeComponent:component]
        #[unsafe(method(removeComponentWithEntity:))]
        #[unsafe(method_family = none)]
        pub unsafe fn removeComponentWithEntity(&self, entity: &GKEntity);

        /// Removes a component from the system
        ///
        /// Does nothing if the component is not in this system
        #[unsafe(method(removeComponent:))]
        #[unsafe(method_family = none)]
        pub unsafe fn removeComponent(&self, component: &ComponentType);

        /// Updates each component with the given delta time since the last update. Each component thus performs its time
        /// based logic with a single message.
        #[unsafe(method(updateWithDeltaTime:))]
        #[unsafe(method_family = none)]
        pub unsafe fn updateWithDeltaTime(&self, seconds: NSTimeInterval);

        /// Returns the class of the specified generic index
        #[unsafe(method(classForGenericArgumentAtIndex:))]
        #[unsafe(method_family = none)]
        pub unsafe fn classForGenericArgumentAtIndex(&self, index: NSUInteger)
            -> &'static AnyClass;
    );
}

/// Methods declared on superclass `NSObject`.
impl<ComponentType: Message + AsRef<GKComponent>> GKComponentSystem<ComponentType> {
    extern_methods!(
        #[unsafe(method(init))]
        #[unsafe(method_family = init)]
        pub unsafe fn init(this: Allocated<Self>) -> Retained<Self>;

        #[unsafe(method(new))]
        #[unsafe(method_family = new)]
        pub unsafe fn new() -> Retained<Self>;
    );
}