using CMLeonOS; using CMLeonOS.Gui.UILib; using System.Collections.Generic; using System.Drawing; namespace CMLeonOS.Gui.Apps { internal class UILibGallery : Process { internal UILibGallery() : base("UILib Gallery", ProcessType.Application) { } private AppWindow window; private Table categoryTable; private Window previewHost; private Window header; private readonly WindowManager wm = ProcessManager.GetProcess(); private readonly List demoWindows = new List(); private FileBrowser fileBrowser; private ToolTip toolTip; private string headerTitle = "UILib Gallery"; private string headerDescription = "Browse and test the current UILib controls."; private const int sidebarWidth = 164; private const int headerHeight = 58; private void SetHeader(string title, string description) { headerTitle = title; headerDescription = description; RenderHeader(); } private void RenderHeader() { header.Clear(Color.FromArgb(235, 241, 248)); header.DrawRectangle(0, 0, header.Width, header.Height, Color.FromArgb(180, 192, 208)); header.DrawString(headerTitle, Color.FromArgb(28, 38, 52), 12, 10); header.DrawString(headerDescription, Color.FromArgb(97, 110, 126), 12, 30); wm.Update(header); } private void ClearPreview() { for (int i = 0; i < demoWindows.Count; i++) { wm.RemoveWindow(demoWindows[i]); } demoWindows.Clear(); previewHost.Clear(Color.FromArgb(250, 252, 255)); previewHost.DrawRectangle(0, 0, previewHost.Width, previewHost.Height, Color.FromArgb(192, 204, 221)); wm.Update(previewHost); } private void AddDemo(Window control) { demoWindows.Add(control); wm.AddWindow(control); } private void ShowButtonsDemo() { ClearPreview(); SetHeader("Button", "Standard action buttons with theme colours and icon support."); TextBlock label = new TextBlock(previewHost, 20, 18, 360, 20); label.Text = "Buttons"; label.Foreground = UITheme.TextPrimary; AddDemo(label); Button primary = new Button(previewHost, 20, 48, 120, 28); primary.Text = "Primary"; primary.OnClick = (_, _) => SetHeader("Button", "Primary button clicked."); AddDemo(primary); Button success = new Button(previewHost, 152, 48, 120, 28); success.Text = "Success"; success.Background = UITheme.Success; success.Border = Color.FromArgb(31, 110, 72); success.OnClick = (_, _) => SetHeader("Button", "Success button clicked."); AddDemo(success); Button neutral = new Button(previewHost, 284, 48, 120, 28); neutral.Text = "Neutral"; neutral.Background = UITheme.SurfaceMuted; neutral.Border = UITheme.SurfaceBorder; neutral.Foreground = UITheme.TextPrimary; neutral.OnClick = (_, _) => SetHeader("Button", "Neutral button clicked."); AddDemo(neutral); ImageBlock iconPreview = new ImageBlock(previewHost, 20, 92, 32, 32); iconPreview.Image = AppManager.DefaultAppIcon.Resize(32, 32); AddDemo(iconPreview); } private void ShowInputsDemo() { ClearPreview(); SetHeader("Input Controls", "Text input, checkbox, switch and slider controls."); TextBox textBox = new TextBox(previewHost, 20, 24, 220, 24); textBox.PlaceholderText = "Type something"; textBox.Changed = () => SetHeader("Input Controls", "TextBox value changed."); AddDemo(textBox); TextBox multi = new TextBox(previewHost, 20, 58, 300, 86); multi.MultiLine = true; multi.Text = "Multi-line TextBox\nUILib demo"; AddDemo(multi); CheckBox checkBox = new CheckBox(previewHost, 340, 24, 180, 20); checkBox.Text = "Enable feature"; checkBox.CheckBoxChanged = (value) => SetHeader("Input Controls", value ? "CheckBox checked." : "CheckBox unchecked."); AddDemo(checkBox); Switch toggle = new Switch(previewHost, 340, 58, 180, 20); toggle.Text = "Animated switch"; toggle.CheckBoxChanged = (value) => SetHeader("Input Controls", value ? "Switch enabled." : "Switch disabled."); AddDemo(toggle); RangeSlider slider = new RangeSlider(previewHost, 340, 96, 220, 30, 0f, 30f, 100f); slider.Changed = (value) => SetHeader("Input Controls", "RangeSlider value: " + ((int)value).ToString()); AddDemo(slider); } private void ShowDropdownDemo() { ClearPreview(); SetHeader("Dropdown", "Single-select dropdown list built on top of Table."); Dropdown dropdown = new Dropdown(previewHost, 20, 28, 200, 24); dropdown.PlaceholderText = "Choose a theme"; dropdown.Items.Add("Ocean"); dropdown.Items.Add("Sunrise"); dropdown.Items.Add("Forest"); dropdown.Items.Add("Mono"); dropdown.RefreshItems(); dropdown.SelectionChanged = (index, text) => SetHeader("Dropdown", "Selected item: " + text); AddDemo(dropdown); TextBlock info = new TextBlock(previewHost, 20, 66, 360, 20); info.Text = "Click the field to expand the dropdown."; info.Foreground = UITheme.TextSecondary; AddDemo(info); } private void ShowTabsDemo() { ClearPreview(); SetHeader("Tabs", "Tab strip control for switching between sections."); Tabs tabs = new Tabs(previewHost, 20, 24, 360, 28); tabs.Items.Add("General"); tabs.Items.Add("Appearance"); tabs.Items.Add("Advanced"); tabs.RefreshItems(); tabs.SelectionChanged = (index, text) => SetHeader("Tabs", "Selected tab: " + text); AddDemo(tabs); TextBlock block = new TextBlock(previewHost, 20, 70, 360, 48); block.Text = "Tabs are ideal for settings and editors."; block.Background = UITheme.AccentLight; block.Foreground = UITheme.TextPrimary; block.HorizontalAlignment = Alignment.Middle; block.VerticalAlignment = Alignment.Middle; AddDemo(block); } private void ShowNumericDemo() { ClearPreview(); SetHeader("NumericUpDown", "Increment and decrement integer values without typing."); NumericUpDown numeric = new NumericUpDown(previewHost, 20, 24, 120, 32); numeric.Minimum = 0; numeric.Maximum = 256; numeric.Step = 8; numeric.Value = 64; numeric.Changed = (value) => SetHeader("NumericUpDown", "Value changed to " + value.ToString()); AddDemo(numeric); TextBlock hint = new TextBlock(previewHost, 160, 28, 320, 24); hint.Text = "Click + / - to change the value."; hint.Foreground = UITheme.TextSecondary; AddDemo(hint); } private void ShowProgressDemo() { ClearPreview(); SetHeader("Progress", "ProgressRing for indeterminate state and ProgressBar for determinate tasks."); ProgressRing ring = new ProgressRing(previewHost, 24, 24, 56, 56); ring.Active = true; AddDemo(ring); TextBlock hint = new TextBlock(previewHost, 100, 20, 380, 24); hint.Text = "ProgressRing keeps animating while Active=true."; hint.Foreground = UITheme.TextSecondary; AddDemo(hint); ProgressBar bar = new ProgressBar(previewHost, 100, 56, 320, 24); bar.Minimum = 0; bar.Maximum = 100; bar.Value = 36; AddDemo(bar); Button minus = new Button(previewHost, 100, 90, 28, 24); minus.Text = "-"; minus.OnClick = (_, _) => { bar.Value -= 10f; SetHeader("Progress", "ProgressBar: " + ((int)(bar.GetPercent() * 100f)).ToString() + "%"); }; AddDemo(minus); Button plus = new Button(previewHost, 136, 90, 28, 24); plus.Text = "+"; plus.OnClick = (_, _) => { bar.Value += 10f; SetHeader("Progress", "ProgressBar: " + ((int)(bar.GetPercent() * 100f)).ToString() + "%"); }; AddDemo(plus); } private void ShowTableDemo() { ClearPreview(); SetHeader("Table", "Selectable list/table control with scrolling and icons."); Table table = new Table(previewHost, 20, 24, 360, 180); table.CellHeight = 24; table.Cells.Add(new TableCell(AppManager.DefaultAppIcon.Resize(20, 20), "First Item", "First")); table.Cells.Add(new TableCell(AppManager.DefaultAppIcon.Resize(20, 20), "Second Item", "Second")); table.Cells.Add(new TableCell(AppManager.DefaultAppIcon.Resize(20, 20), "Third Item", "Third")); table.Cells.Add(new TableCell("Text-only row", "Text")); table.TableCellSelected = (index) => { if (index >= 0 && index < table.Cells.Count) { SetHeader("Table", "Selected row: " + table.Cells[index].Text); } }; table.Render(); AddDemo(table); } private void ShowBarsDemo() { ClearPreview(); SetHeader("Bars And Blocks", "ShortcutBar, TextBlock and ImageBlock examples."); ShortcutBar shortcutBar = new ShortcutBar(previewHost, 20, 20, 360, 24); shortcutBar.Background = UITheme.SurfaceMuted; shortcutBar.Foreground = UITheme.TextPrimary; shortcutBar.Cells.Add(new ShortcutBarCell("File", () => SetHeader("Bars And Blocks", "ShortcutBar: File"))); shortcutBar.Cells.Add(new ShortcutBarCell("Edit", () => SetHeader("Bars And Blocks", "ShortcutBar: Edit"))); shortcutBar.Cells.Add(new ShortcutBarCell("View", () => SetHeader("Bars And Blocks", "ShortcutBar: View"))); shortcutBar.Render(); AddDemo(shortcutBar); TextBlock centered = new TextBlock(previewHost, 20, 62, 220, 48); centered.Text = "Centered TextBlock"; centered.Background = UITheme.AccentLight; centered.Foreground = UITheme.TextPrimary; centered.HorizontalAlignment = Alignment.Middle; centered.VerticalAlignment = Alignment.Middle; AddDemo(centered); ImageBlock image = new ImageBlock(previewHost, 260, 62, 48, 48); image.Image = AppManager.DefaultAppIcon.Resize(48, 48); image.Alpha = true; AddDemo(image); StatusBar statusBar = new StatusBar(previewHost, 20, 132, 360, 24); statusBar.Text = "Ready"; statusBar.DetailText = "UILib Demo"; AddDemo(statusBar); Separator separator = new Separator(previewHost, 20, 172, 360, 8); separator.Background = Color.FromArgb(250, 252, 255); separator.Foreground = UITheme.SurfaceBorder; AddDemo(separator); } private void ShowTreeDemo() { ClearPreview(); SetHeader("TreeView", "Hierarchical tree control for folders, settings and project structures."); TreeView tree = new TreeView(previewHost, 20, 24, 300, 180); TreeNode rootA = new TreeNode("System"); rootA.Expanded = true; rootA.Children.Add(new TreeNode("Apps")); rootA.Children.Add(new TreeNode("Config")); TreeNode rootB = new TreeNode("User"); rootB.Children.Add(new TreeNode("Desktop")); rootB.Children.Add(new TreeNode("Documents")); rootB.Children.Add(new TreeNode("Pictures")); tree.Nodes.Add(rootA); tree.Nodes.Add(rootB); tree.NodeSelected = (node) => SetHeader("TreeView", "Selected node: " + node.Text); tree.Render(); AddDemo(tree); } private void ShowDialogsDemo() { ClearPreview(); SetHeader("Dialogs", "Dialog-style components that open in separate windows."); Button messageButton = new Button(previewHost, 20, 28, 140, 28); messageButton.Text = "MessageBox"; messageButton.OnClick = (_, _) => { new MessageBox(this, "UILib Gallery", "This is a MessageBox demo.").Show(); }; AddDemo(messageButton); Button promptButton = new Button(previewHost, 172, 28, 140, 28); promptButton.Text = "PromptBox"; promptButton.OnClick = (_, _) => { PromptBox prompt = new PromptBox(this, "UILib Gallery", "Enter sample text.", "Hello", (value) => { SetHeader("Dialogs", "Prompt result: " + (string.IsNullOrWhiteSpace(value) ? "(empty)" : value)); }); prompt.Show(); }; AddDemo(promptButton); Button fileBrowserButton = new Button(previewHost, 324, 28, 140, 28); fileBrowserButton.Text = "FileBrowser"; fileBrowserButton.OnClick = (_, _) => { fileBrowser = new FileBrowser(this, wm, (selectedPath) => { SetHeader("Dialogs", "FileBrowser selected: " + (string.IsNullOrWhiteSpace(selectedPath) ? "(cancelled)" : selectedPath)); }); fileBrowser.Show(); }; AddDemo(fileBrowserButton); Button notificationButton = new Button(previewHost, 20, 68, 140, 28); notificationButton.Text = "Notification"; notificationButton.OnClick = (_, _) => { Notification notification = new Notification(this, "UILib Gallery", "This is a toast notification."); notification.Show(); }; AddDemo(notificationButton); Button toolTipButton = new Button(previewHost, 172, 68, 140, 28); toolTipButton.Text = "ToolTip"; toolTipButton.OnClick = (_, _) => { if (toolTip == null) { toolTip = new ToolTip(this, wm); } toolTip.Show(toolTipButton, "Manual ToolTip demo"); SetHeader("Dialogs", "ToolTip shown near the button."); }; toolTipButton.OnUnfocused = () => toolTip?.Hide(); AddDemo(toolTipButton); } private void CategorySelected(int index) { switch (index) { case 0: ShowButtonsDemo(); break; case 1: ShowInputsDemo(); break; case 2: ShowDropdownDemo(); break; case 3: ShowTabsDemo(); break; case 4: ShowNumericDemo(); break; case 5: ShowProgressDemo(); break; case 6: ShowTableDemo(); break; case 7: ShowTreeDemo(); break; case 8: ShowBarsDemo(); break; case 9: ShowDialogsDemo(); break; } } private void Relayout() { categoryTable.MoveAndResize(0, 0, sidebarWidth, window.Height); header.MoveAndResize(sidebarWidth, 0, window.Width - sidebarWidth, headerHeight); previewHost.MoveAndResize(sidebarWidth, headerHeight, window.Width - sidebarWidth, window.Height - headerHeight); categoryTable.Render(); RenderHeader(); ClearPreview(); if (categoryTable.SelectedCellIndex < 0) { categoryTable.SelectedCellIndex = 0; } CategorySelected(categoryTable.SelectedCellIndex); } public override void Start() { base.Start(); window = new AppWindow(this, 180, 110, 860, 520); window.Title = "UILib Gallery"; window.Icon = AppManager.DefaultAppIcon; window.CanResize = true; window.UserResized = Relayout; window.Closing = TryStop; wm.AddWindow(window); categoryTable = new Table(window, 0, 0, sidebarWidth, window.Height); categoryTable.AllowDeselection = false; categoryTable.CellHeight = 26; categoryTable.TextAlignment = Alignment.Middle; categoryTable.Background = Color.FromArgb(242, 246, 252); categoryTable.Border = Color.FromArgb(182, 194, 210); categoryTable.SelectedBackground = Color.FromArgb(216, 231, 255); categoryTable.SelectedBorder = UITheme.Accent; categoryTable.SelectedForeground = UITheme.TextPrimary; categoryTable.TableCellSelected = CategorySelected; categoryTable.Cells.Add(new TableCell("Buttons")); categoryTable.Cells.Add(new TableCell("Inputs")); categoryTable.Cells.Add(new TableCell("Dropdown")); categoryTable.Cells.Add(new TableCell("Tabs")); categoryTable.Cells.Add(new TableCell("Numeric")); categoryTable.Cells.Add(new TableCell("Progress")); categoryTable.Cells.Add(new TableCell("Table")); categoryTable.Cells.Add(new TableCell("TreeView")); categoryTable.Cells.Add(new TableCell("Bars && Blocks")); categoryTable.Cells.Add(new TableCell("Dialogs")); wm.AddWindow(categoryTable); header = new Window(this, window, sidebarWidth, 0, window.Width - sidebarWidth, headerHeight); wm.AddWindow(header); previewHost = new Window(this, window, sidebarWidth, headerHeight, window.Width - sidebarWidth, window.Height - headerHeight); wm.AddWindow(previewHost); categoryTable.SelectedCellIndex = 0; Relayout(); wm.Update(window); } public override void Run() { } } }