rusteal 0.8.0

Rust bindings for Unreal Engine 5.8.2
use bindings::core_ue::Object;
use bindings::data_validation::{EditorValidatorBase, EditorValidatorBaseExt};
use rusteal_runtime::runtime::UObjectRef;
use rusteal_runtime::{uclass, uclass_impl};

const INVALID: u8 = 0;
const VALID: u8 = 1;

#[uclass(parent = EditorValidatorBase)]
pub struct {{ plugin }}NameValidator {}

#[uclass_impl]
impl {{ plugin }}NameValidator {
    #[ufunction(Override, name = "K2_CanValidateAsset")]
    fn can_validate_asset(&self, asset: UObjectRef<Object>) -> bool {
        asset.is_valid()
    }

    #[ufunction(Override, name = "K2_ValidateLoadedAsset")]
    fn validate_loaded_asset(&mut self, asset: UObjectRef<Object>) -> u8 {
        let Ok(name) = asset.get_name() else {
            return VALID;
        };

        let Ok(me) = self.as_ref().checked() else {
            return VALID;
        };

        if !has_type_prefix(&name) {
            me.asset_fails(
                asset,
                &format!("'{name}' has no type prefix (SM_, T_, BP_...)"),
            );

            INVALID
        } else {
            me.asset_passes(asset);

            VALID
        }
    }
}

fn has_type_prefix(name: &str) -> bool {
    match name.split_once('_') {
        Some((prefix, rest)) => {
            !prefix.is_empty() && !rest.is_empty() && prefix.chars().all(|c| c.is_ascii_uppercase())
        }
        None => false,
    }
}