feat: add temp template.
This commit is contained in:
@@ -12,6 +12,7 @@ public static class MenuKeys
|
||||
public const string MenuKeyDrawer = "Drawer";
|
||||
public const string MenuKeyDualBadge = "DualBadge";
|
||||
public const string MenuKeyEnumSelector = "EnumSelector";
|
||||
public const string MenuKeyForm = "Form";
|
||||
public const string MenuKeyImageViewer = "ImageViewer";
|
||||
public const string MenuKeyIpBox = "IPv4Box";
|
||||
public const string MenuKeyIconButton = "IconButton";
|
||||
|
||||
27
demo/Ursa.Demo/Pages/FormDemo.axaml
Normal file
27
demo/Ursa.Demo/Pages/FormDemo.axaml
Normal file
@@ -0,0 +1,27 @@
|
||||
<UserControl xmlns="https://github.com/avaloniaui"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
||||
xmlns:vm="clr-namespace:Ursa.Demo.ViewModels;assembly=Ursa.Demo"
|
||||
xmlns:u="https://irihi.tech/ursa"
|
||||
x:DataType="vm:FormDemoViewModel"
|
||||
x:CompileBindings="True"
|
||||
x:Class="Ursa.Demo.Pages.FormDemo">
|
||||
<StackPanel>
|
||||
<u:Form DataContext="{Binding Model}" >
|
||||
<u:FormGroup Header="Information">
|
||||
<TextBox u:Form.Label="Name" Text="{Binding Name}"/>
|
||||
<TextBox u:Form.Label="Email" Text="{Binding Email}"/>
|
||||
</u:FormGroup>
|
||||
<u:FormItem>
|
||||
<CalendarDatePicker u:Form.Label="Date" SelectedDate="{Binding Date}" />
|
||||
</u:FormItem>
|
||||
</u:Form>
|
||||
<StackPanel>
|
||||
<TextBlock Text="{Binding Model.Name}"></TextBlock>
|
||||
<TextBlock Text="{Binding Model.Email}"></TextBlock>
|
||||
<TextBlock Text="{Binding Model.Date}"></TextBlock>
|
||||
</StackPanel>
|
||||
</StackPanel>
|
||||
</UserControl>
|
||||
13
demo/Ursa.Demo/Pages/FormDemo.axaml.cs
Normal file
13
demo/Ursa.Demo/Pages/FormDemo.axaml.cs
Normal file
@@ -0,0 +1,13 @@
|
||||
using Avalonia;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Markup.Xaml;
|
||||
|
||||
namespace Ursa.Demo.Pages;
|
||||
|
||||
public partial class FormDemo : UserControl
|
||||
{
|
||||
public FormDemo()
|
||||
{
|
||||
InitializeComponent();
|
||||
}
|
||||
}
|
||||
43
demo/Ursa.Demo/ViewModels/FormDemoViewModel.cs
Normal file
43
demo/Ursa.Demo/ViewModels/FormDemoViewModel.cs
Normal file
@@ -0,0 +1,43 @@
|
||||
using System;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using CommunityToolkit.Mvvm.ComponentModel;
|
||||
|
||||
namespace Ursa.Demo.ViewModels;
|
||||
|
||||
public partial class FormDemoViewModel: ObservableObject
|
||||
{
|
||||
[ObservableProperty] private DataModel _model;
|
||||
|
||||
public FormDemoViewModel()
|
||||
{
|
||||
Model = new DataModel();
|
||||
}
|
||||
}
|
||||
|
||||
public partial class DataModel : ObservableObject
|
||||
{
|
||||
private string _name;
|
||||
|
||||
[MinLength(10)]
|
||||
public string Name
|
||||
{
|
||||
get=>_name;
|
||||
set => SetProperty(ref _name, value);
|
||||
}
|
||||
|
||||
private string _email;
|
||||
|
||||
[EmailAddress]
|
||||
public string Email
|
||||
{
|
||||
get=>_email;
|
||||
set => SetProperty(ref _email, value);
|
||||
}
|
||||
|
||||
private DateTime _date;
|
||||
public DateTime Date
|
||||
{
|
||||
get => _date;
|
||||
set => SetProperty(ref _date, value);
|
||||
}
|
||||
}
|
||||
@@ -34,6 +34,7 @@ public class MainViewViewModel : ViewModelBase
|
||||
MenuKeys.MenuKeyDrawer => new DrawerDemoViewModel(),
|
||||
MenuKeys.MenuKeyDualBadge => new DualBadgeDemoViewModel(),
|
||||
MenuKeys.MenuKeyEnumSelector => new EnumSelectorDemoViewModel(),
|
||||
MenuKeys.MenuKeyForm => new FormDemoViewModel(),
|
||||
MenuKeys.MenuKeyImageViewer => new ImageViewerDemoViewModel(),
|
||||
MenuKeys.MenuKeyIconButton => new IconButtonDemoViewModel(),
|
||||
MenuKeys.MenuKeyIpBox => new IPv4BoxDemoViewModel(),
|
||||
|
||||
@@ -21,6 +21,7 @@ public class MenuViewModel: ViewModelBase
|
||||
new() { MenuHeader = "Drawer", Key = MenuKeys.MenuKeyDrawer },
|
||||
new() { MenuHeader = "DualBadge", Key = MenuKeys.MenuKeyDualBadge },
|
||||
new() { MenuHeader = "Enum Selector", Key = MenuKeys.MenuKeyEnumSelector },
|
||||
new() { MenuHeader = "Form", Key = MenuKeys.MenuKeyForm },
|
||||
new() { MenuHeader = "Icon Button", Key = MenuKeys.MenuKeyIconButton },
|
||||
new() { MenuHeader = "ImageViewer", Key = MenuKeys.MenuKeyImageViewer },
|
||||
new() { MenuHeader = "IPv4Box", Key = MenuKeys.MenuKeyIpBox },
|
||||
|
||||
34
src/Ursa.Themes.Semi/Controls/Form.axaml
Normal file
34
src/Ursa.Themes.Semi/Controls/Form.axaml
Normal file
@@ -0,0 +1,34 @@
|
||||
<ResourceDictionary xmlns="https://github.com/avaloniaui"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:u="https://irihi.tech/ursa">
|
||||
<!-- Add Resources Here -->
|
||||
<ControlTheme x:Key="{x:Type u:Form}" TargetType="u:Form">
|
||||
<Setter Property="Template">
|
||||
<ControlTemplate TargetType="u:Form">
|
||||
<ItemsPresenter ItemsPanel="{TemplateBinding ItemsPanel}"></ItemsPresenter>
|
||||
</ControlTemplate>
|
||||
</Setter>
|
||||
</ControlTheme>
|
||||
|
||||
<ControlTheme x:Key="{x:Type u:FormGroup}" TargetType="u:FormGroup">
|
||||
<Setter Property="Template">
|
||||
<ControlTemplate TargetType="u:FormGroup">
|
||||
<StackPanel>
|
||||
<ContentPresenter Content="{TemplateBinding Header}"/>
|
||||
<ItemsPresenter ItemsPanel="{TemplateBinding ItemsPanel}"/>
|
||||
</StackPanel>
|
||||
</ControlTemplate>
|
||||
</Setter>
|
||||
</ControlTheme>
|
||||
|
||||
<ControlTheme x:Key="{x:Type u:FormItem}" TargetType="u:FormItem">
|
||||
<Setter Property="Template">
|
||||
<ControlTemplate TargetType="u:FormItem">
|
||||
<StackPanel Orientation="Horizontal">
|
||||
<TextBlock Text="{TemplateBinding Label}" />
|
||||
<ContentPresenter Content="{TemplateBinding Content}"/>
|
||||
</StackPanel>
|
||||
</ControlTemplate>
|
||||
</Setter>
|
||||
</ControlTheme>
|
||||
</ResourceDictionary>
|
||||
@@ -11,6 +11,7 @@
|
||||
<ResourceInclude Source="Drawer.axaml" />
|
||||
<ResourceInclude Source="DualBadge.axaml" />
|
||||
<ResourceInclude Source="EnumSelector.axaml" />
|
||||
<ResourceInclude Source="Form.axaml" />
|
||||
<ResourceInclude Source="IconButton.axaml" />
|
||||
<ResourceInclude Source="ImageViewer.axaml" />
|
||||
<ResourceInclude Source="IPv4Box.axaml" />
|
||||
|
||||
@@ -1,25 +1,32 @@
|
||||
using Avalonia;
|
||||
using Avalonia.Collections;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Markup.Xaml.Templates;
|
||||
using Avalonia.Metadata;
|
||||
|
||||
namespace Ursa.Controls;
|
||||
|
||||
public class Form: ItemsControl
|
||||
{
|
||||
|
||||
public static readonly StyledProperty<AvaloniaList<FormItem>> ItemsProperty = AvaloniaProperty.Register<Form, AvaloniaList<FormItem>>(
|
||||
"Items");
|
||||
public static readonly AttachedProperty<string> LabelProperty =
|
||||
AvaloniaProperty.RegisterAttached<Form, Control, string>("Label");
|
||||
public static void SetLabel(Control obj, string value) => obj.SetValue(LabelProperty, value);
|
||||
public static string GetLabel(Control obj) => obj.GetValue(LabelProperty);
|
||||
|
||||
public AvaloniaList<FormItem> Items
|
||||
{
|
||||
get => GetValue(ItemsProperty);
|
||||
set => SetValue(ItemsProperty, value);
|
||||
}
|
||||
|
||||
public void AddChild(object child)
|
||||
public static readonly AttachedProperty<bool> IsRequiredProperty =
|
||||
AvaloniaProperty.RegisterAttached<Form, Control, bool>("IsRequired");
|
||||
public static void SetIsRequired(Control obj, bool value) => obj.SetValue(IsRequiredProperty, value);
|
||||
public static bool GetIsRequired(Control obj) => obj.GetValue(IsRequiredProperty);
|
||||
|
||||
protected override bool NeedsContainerOverride(object? item, int index, out object? recycleKey)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
recycleKey = null;
|
||||
return item is FormItem or FormGroup;
|
||||
}
|
||||
|
||||
protected override Control CreateContainerForItemOverride(object? item, int index, object? recycleKey)
|
||||
{
|
||||
if (item is not Control control) return new FormItem();
|
||||
string label = GetLabel(control);
|
||||
bool isRequired = GetIsRequired(control);
|
||||
return new FormItem() { Label = label, IsRequired = isRequired, Content = control };
|
||||
}
|
||||
}
|
||||
@@ -3,7 +3,19 @@ using Avalonia.Controls.Primitives;
|
||||
|
||||
namespace Ursa.Controls;
|
||||
|
||||
public class FormGroup: HeaderedItemsControl, IFormItem
|
||||
public class FormGroup: HeaderedItemsControl
|
||||
{
|
||||
|
||||
protected override bool NeedsContainerOverride(object? item, int index, out object? recycleKey)
|
||||
{
|
||||
recycleKey = null;
|
||||
return item is not FormItem or FormGroup;
|
||||
}
|
||||
|
||||
protected override Control CreateContainerForItemOverride(object? item, int index, object? recycleKey)
|
||||
{
|
||||
if (item is not Control control) return new FormItem();
|
||||
var label = Form.GetLabel(control);
|
||||
var isRequired = Form.GetIsRequired(control);
|
||||
return new FormItem() { Label = label, IsRequired = isRequired, Content = control };
|
||||
}
|
||||
}
|
||||
@@ -1,8 +1,27 @@
|
||||
using Avalonia.Controls.Primitives;
|
||||
using Avalonia;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Controls.Primitives;
|
||||
|
||||
namespace Ursa.Controls;
|
||||
|
||||
public class FormItem: TemplatedControl, IFormItem
|
||||
public class FormItem: ContentControl
|
||||
{
|
||||
public static readonly StyledProperty<string> LabelProperty = AvaloniaProperty.Register<FormItem, string>(
|
||||
nameof(Label));
|
||||
|
||||
public string Label
|
||||
{
|
||||
get => GetValue(LabelProperty);
|
||||
set => SetValue(LabelProperty, value);
|
||||
}
|
||||
|
||||
public static readonly StyledProperty<bool> IsRequiredProperty = AvaloniaProperty.Register<FormItem, bool>(
|
||||
nameof(IsRequired));
|
||||
|
||||
public bool IsRequired
|
||||
{
|
||||
get => GetValue(IsRequiredProperty);
|
||||
set => SetValue(IsRequiredProperty, value);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,9 +0,0 @@
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Controls.Primitives;
|
||||
|
||||
namespace Ursa.Controls;
|
||||
|
||||
public interface IFormItem
|
||||
{
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user