use objc2::rc::{Allocated, Retained};
use objc2::runtime::AnyClass;
use objc2::{msg_send, msg_send_id};
use objc2_app_kit::{NSColor, NSView};
#[derive(Clone, Copy, Debug)]
pub(crate) enum GlassStyle {
Regular,
Clear,
}
impl GlassStyle {
fn raw(self) -> isize {
match self {
GlassStyle::Regular => 0,
GlassStyle::Clear => 1,
}
}
}
#[derive(Debug)]
pub(crate) struct GlassEffect {
view: Retained<NSView>,
}
impl GlassEffect {
#[inline]
pub(crate) fn class_available() -> bool {
AnyClass::get("NSGlassEffectView").is_some()
}
pub(crate) fn new() -> Option<Self> {
let cls = AnyClass::get("NSGlassEffectView")?;
let view: Retained<NSView> = unsafe {
let alloc: Allocated<NSView> = msg_send_id![cls, alloc];
msg_send_id![alloc, init]
};
Some(GlassEffect { view })
}
pub(crate) fn set_style(&self, style: GlassStyle) {
let raw = style.raw();
unsafe {
let _: () = msg_send![&*self.view, setStyle: raw];
}
}
pub(crate) fn set_tint_color_with_opacity(&self, color: &NSColor, opacity: f64) {
let opacity = opacity.clamp(0.0, 1.0);
unsafe {
let tinted: Retained<NSColor> =
msg_send_id![color, colorWithAlphaComponent: opacity];
let _: () = msg_send![&*self.view, setTintColor: &*tinted];
}
}
pub(crate) fn set_corner_radius(&self, radius: f64) {
unsafe {
let _: () = msg_send![&*self.view, setCornerRadius: radius];
}
}
pub(crate) fn set_content_view(&self, content: &NSView) {
unsafe {
let _: () = msg_send![&*self.view, setContentView: content];
}
}
pub(crate) fn content_view(&self) -> Option<Retained<NSView>> {
unsafe { msg_send_id![&*self.view, contentView] }
}
pub(crate) fn as_ns_view(&self) -> &NSView {
&self.view
}
}