feat(ui): wire avalonia desktop ui to data and worker
App: build a ServiceProvider in Program.cs (AppSettings, SqliteConnectionFactory, all repositories, GitService, WorkerClient, all view-models), apply schema, then hand control to Avalonia. App.OnFrameworkInitializationCompleted resolves MainWindowViewModel from the container. Ui: - AppSettings POCO loaded from ~/.todo-app/ui.config.json (db path, hub url). - WorkerClient wraps HubConnection with auto-reconnect, exposes IsConnected and ActiveTasks plus C# events for TaskStarted/Finished/Message/Updated and WorktreeUpdated; all inbound events are marshalled to the UI thread. - ViewModels: MainWindow (lists CRUD via ListEditor dialog), TaskList (load by list, add/edit/delete, auto WakeQueue on agent+queued create), TaskItem (RunNow gated on connection + status), TaskDetail (description, result, live ndjson rolling buffer of 500 lines, worktree branch/diff with merge/keep/ discard via GitService), StatusBar, ListEditor, TaskEditor. - Views: 3-pane MainWindow (lists | tasks | detail) with GridSplitters, status bar, dialog windows for the editors. Status badges via StatusColorConverter. - Markdown rendering, folder picker, delete-confirmation, settings dialog and scroll-to-bottom on the live log are intentionally TODO -- functional scaffold only. Tests: also debounce the FIFO queue test (poll instead of Task.Delay(200)) so the assertion isn't racy when the suite runs alongside the slower git tests. 38 tests pass. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
40
src/ClaudeDo.Ui/Views/TaskListView.axaml
Normal file
40
src/ClaudeDo.Ui/Views/TaskListView.axaml
Normal file
@@ -0,0 +1,40 @@
|
||||
<UserControl xmlns="https://github.com/avaloniaui"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:vm="using:ClaudeDo.Ui.ViewModels"
|
||||
xmlns:conv="using:ClaudeDo.Ui.Converters"
|
||||
x:Class="ClaudeDo.Ui.Views.TaskListView"
|
||||
x:DataType="vm:TaskListViewModel">
|
||||
<DockPanel>
|
||||
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal" Margin="4">
|
||||
<TextBlock Text="Tasks" FontWeight="Bold" FontSize="14" VerticalAlignment="Center" Margin="4,0"/>
|
||||
</StackPanel>
|
||||
<StackPanel DockPanel.Dock="Bottom" Orientation="Horizontal" Spacing="4" Margin="4">
|
||||
<Button Content="+ Task" Command="{Binding AddTaskCommand}" MinWidth="60"/>
|
||||
<Button Content="Edit" Command="{Binding EditTaskCommand}" MinWidth="50"/>
|
||||
<Button Content="Delete" Command="{Binding DeleteTaskCommand}" MinWidth="50"/>
|
||||
</StackPanel>
|
||||
<ListBox ItemsSource="{Binding Tasks}"
|
||||
SelectedItem="{Binding SelectedTask}"
|
||||
Margin="4">
|
||||
<ListBox.ItemTemplate>
|
||||
<DataTemplate x:DataType="vm:TaskItemViewModel">
|
||||
<Grid ColumnDefinitions="*,Auto,Auto" Margin="4,2">
|
||||
<StackPanel Grid.Column="0">
|
||||
<TextBlock Text="{Binding Title}" FontWeight="SemiBold"/>
|
||||
<TextBlock Text="{Binding TagsText}" FontSize="10" Foreground="Gray"
|
||||
IsVisible="{Binding TagsText, Converter={x:Static StringConverters.IsNotNullOrEmpty}}"/>
|
||||
</StackPanel>
|
||||
<Border Grid.Column="1" CornerRadius="3" Padding="6,2" Margin="4,0"
|
||||
Background="{Binding StatusText, Converter={x:Static conv:StatusColorConverter.Instance}}"
|
||||
VerticalAlignment="Center">
|
||||
<TextBlock Text="{Binding StatusText}" Foreground="White" FontSize="11"/>
|
||||
</Border>
|
||||
<Button Grid.Column="2" Content="Run" Command="{Binding RunNowCommand}"
|
||||
Margin="4,0,0,0" VerticalAlignment="Center" Padding="8,2"
|
||||
FontSize="11"/>
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
</ListBox.ItemTemplate>
|
||||
</ListBox>
|
||||
</DockPanel>
|
||||
</UserControl>
|
||||
Reference in New Issue
Block a user