windjammer-ui 0.3.6

Cross-platform UI framework for Windjammer (Web, Desktop, Mobile)
Documentation
// Menu and MenuItem - Dropdown menu components

pub struct Menu {
    items: Vec<string>,
    trigger: string,
    class: string,
}

impl Menu {
    pub fn new(trigger: string) -> Menu {
        Menu {
            items: Vec::new(),
            trigger,
            class: String::new(),
        }
    }
    
    pub fn item(item: string) -> Menu {
        self.items.push(item)
        self
    }
    
    pub fn class(class: string) -> Menu {
        self.class = class
        self
    }
    
    pub fn render() -> string {
        let mut html = String::new()
        html.push_str("<div class=\"wj-menu ")
        html.push_str(self.class.as_str())
        html.push_str("\" style=\"position: relative; display: inline-block;\">")
        
        // Trigger button
        html.push_str(self.trigger.as_str())
        
        // Menu items
        html.push_str("<div class=\"wj-menu-items\" style=\"position: absolute; top: 100%; left: 0; margin-top: 4px; background: white; border: 1px solid #e5e7eb; border-radius: 8px; box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1); min-width: 200px; z-index: 1000; display: none;\">")
        
        for item in self.items {
            html.push_str(item.as_str())
        }
        
        html.push_str("</div>")
        html.push_str("</div>")
        
        // Add hover behavior
        html.push_str("<style>.wj-menu:hover .wj-menu-items { display: block; }</style>")
        
        html
    }
}

pub struct MenuItem {
    label: string,
    icon: string,
    href: string,
    disabled: bool,
    class: string,
}

impl MenuItem {
    pub fn new(label: string) -> MenuItem {
        MenuItem {
            label,
            icon: String::new(),
            href: "#".to_string(),
            disabled: false,
            class: String::new(),
        }
    }
    
    pub fn icon(icon: string) -> MenuItem {
        self.icon = icon
        self
    }
    
    pub fn href(href: string) -> MenuItem {
        self.href = href
        self
    }
    
    pub fn disabled(disabled: bool) -> MenuItem {
        self.disabled = disabled
        self
    }
    
    pub fn class(class: string) -> MenuItem {
        self.class = class
        self
    }
    
    pub fn render() -> string {
        let disabled_style = if self.disabled {
            " opacity: 0.5; cursor: not-allowed;"
        } else {
            " cursor: pointer;"
        }
        
        let mut html = String::new()
        html.push_str("<a href=\"")
        html.push_str(self.href.as_str())
        html.push_str("\" class=\"wj-menu-item ")
        html.push_str(self.class.as_str())
        html.push_str("\" style=\"display: flex; align-items: center; gap: 8px; padding: 10px 16px; color: #374151; text-decoration: none;")
        html.push_str(disabled_style)
        html.push_str(" transition: background-color 0.2s;\">")
        
        if !self.icon.is_empty() {
            html.push_str("<span>")
            html.push_str(self.icon.as_str())
            html.push_str("</span>")
        }
        
        html.push_str("<span>")
        html.push_str(self.label.as_str())
        html.push_str("</span>")
        html.push_str("</a>")
        
        // Add hover effect
        html.push_str("<style>.wj-menu-item:hover:not([style*='cursor: not-allowed']) { background-color: #f3f4f6; }</style>")
        
        html
    }
}