using System; using Avalonia; using Avalonia.Controls; using Avalonia.Input; using Avalonia.Interactivity; using Avalonia.VisualTree; using AdvancedCalculator.ViewModels; using AdvancedCalculator.Models; using Avalonia.Controls.Presenters; namespace AdvancedCalculator.Views; public partial class MainView : UserControl { public MainView() { InitializeComponent(); this.AttachedToVisualTree += OnAttachedToVisualTree; this.DetachedFromVisualTree += OnDetachedFromVisualTree; } private MainViewModel? _vm; private ListBox? _historyList; // Functions flyout is handled via per-item Tapped in XAML private void OnAttachedToVisualTree(object? sender, VisualTreeAttachmentEventArgs e) { _vm = DataContext as MainViewModel; if (_vm is not null) { _vm.CopyRequested += OnCopyRequested; } _historyList = this.FindControl("HistoryList"); if (_historyList is not null) { // Handle taps anywhere in a history row to copy output text _historyList.AddHandler(InputElement.TappedEvent, OnHistoryTapped, RoutingStrategies.Tunnel | RoutingStrategies.Bubble); } // Functions flyout wiring is done via Opened/Closed events } private void OnDetachedFromVisualTree(object? sender, VisualTreeAttachmentEventArgs e) { if (_vm is not null) { _vm.CopyRequested -= OnCopyRequested; } if (_historyList is not null) { _historyList.RemoveHandler(InputElement.TappedEvent, OnHistoryTapped); _historyList = null; } _vm = null; } private async void OnCopyRequested(object? sender, string text) { var top = TopLevel.GetTopLevel(this); if (top?.Clipboard is null) return; try { await top.Clipboard.SetTextAsync(text); } catch { // Ignore clipboard errors; e.g., browser permission or missing gesture context } } private void OnHistoryTapped(object? sender, TappedEventArgs e) { // Find the ListBoxItem the tap originated from var source = e.Source as ContentPresenter; var container = source?.FindAncestorOfType(); if (container?.DataContext is not HistoryItem item) return; var vm = DataContext as MainViewModel; if (vm?.CopyHistoryOutputCommand.CanExecute(item) == true) { vm.CopyHistoryOutputCommand.Execute(item); // Mark handled to avoid unintended selection change on tap e.Handled = true; } } private void OnFunctionsItemTapped(object? sender, TappedEventArgs e) { var lbi = (e.Source as Control)?.FindAncestorOfType(); if (lbi?.DataContext is FunctionDefinitionItem item && _vm?.InsertFunctionCommand.CanExecute(item) == true) { _vm.InsertFunctionCommand.Execute(item); // Return focus to the input box so the caret is active var input = this.FindControl("InputBox"); input?.Focus(); e.Handled = true; } } // Removed Opened/Closed dynamic wiring; handled directly in XAML. }