use crate::if_node_is_valid;
use godot::classes::control::SizeFlags;
use godot::classes::{
	AnimationLibrary, AnimationMixer, Control, EditorInspectorPlugin, EditorResourcePicker, HBoxContainer,
	IEditorInspectorPlugin, Label,
};
use godot::prelude::*;

#[derive(GodotClass)]
#[class(base = EditorInspectorPlugin, tool, init)]
pub struct GlobalLibraryButtonPlugin {
	base: Base<EditorInspectorPlugin>,
}

#[godot_api]
impl IEditorInspectorPlugin for GlobalLibraryButtonPlugin {
	fn can_handle(&self, object: Option<Gd<Object>>) -> bool {
		object
			.map(|object| object.is_class(&GString::from("AnimationMixer")))
			.unwrap_or(false)
	}

	fn parse_category(&mut self, object: Option<Gd<Object>>, category: GString) {
		if category == GString::from("AnimationMixer") {
			let animation_player: Gd<AnimationMixer> = if_node_is_valid!([AnimationMixer]; object);
			self.base_mut()
				.add_custom_control(&build_setter_control(animation_player));
		}
	}
}

fn build_setter_control(mut animation_player: Gd<AnimationMixer>) -> Gd<Control> {
	let mut hbox = HBoxContainer::new_alloc();
	hbox.add_theme_constant_override("spacing", 5);

	let mut label = Label::new_alloc();
	label.set_text(&GString::from("Set global"));
	label.set_h_size_flags(SizeFlags::EXPAND_FILL);
	hbox.add_child(&label);

	let mut resource_picker = EditorResourcePicker::new_alloc();
	resource_picker.set_base_type("AnimationLibrary");
	resource_picker.connect(
		"resource_changed",
		&Callable::from_local_fn("set_root_anim_library", move |args| {
			let library = match args.first().and_then(|r| r.try_to::<Gd<AnimationLibrary>>().ok()) {
				Some(library) => library,
				None => return Ok(Variant::nil()),
			};
			// A library without an identifier is set as the global library, and doesn't need a prefix in gdscript
			animation_player.add_animation_library("", &library);
			Ok(Variant::nil())
		}),
	);
	resource_picker.set_h_size_flags(SizeFlags::EXPAND_FILL);
	hbox.add_child(&resource_picker);

	hbox.upcast::<Control>()
}