У меня не получается создать пользовательский элемент который будет авто масштабировать в таблице (grid). Результат которого я хочу добиться это вот:
Т.е чтобы в центре надпись и под ней сама масштабировалась.
Только здесь можно убрать самую верхнюю надпись, и степени окисления которые находятся в правом верхнем углу. Вот мой набросок ( с градиентом и цветом решу в конце, это не сложно).
Но здесь не получается по центру выравнять буквы ( в данном варианте Br). Также здесь может быть минимально одна буква, а максимально 3 буквы. Но так получается что съезжает влево если одна буква или две, если 3 буквы то по размеру часть их скрывалась, я сделал DockPanel и объединил ячейки в центре как на скрине:
Но не получается желаемый результат. Я много разных вариантов перепробовал с border, grid и другими контейнерами. Кто может подсказать как это решить? Я бы просто налепил картинок с уже задаными значениями, но я хочу парсить из базы данных значения и заполнять этими элементами таблицу. Код ниже:
<UserControl x:Class="ChemicalBase.Elements.UserControl1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:ChemicalBase.Elements"
mc:Ignorable="d"
d:DesignHeight="50" d:DesignWidth="50" MinHeight="50" MinWidth="50" MaxWidth="50" MaxHeight="50">
<Border BorderBrush="White" Background="White">
<Grid Background="#FF58B26D" Margin="2">
<Grid.RowDefinitions>
<RowDefinition Height="*"/>
<RowDefinition Height="*"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="9*"/>
<ColumnDefinition Width="9*"/>
<ColumnDefinition Width="5*"/>
</Grid.ColumnDefinitions>
<DockPanel Grid.Row="1" Grid.ColumnSpan="3" LastChildFill="False">
<TextBlock HorizontalAlignment="Center" DockPanel.Dock="left" TextWrapping="Wrap" Text="Uuh" Width="25" Foreground="White" FontWeight="Bold" Grid.Column="1" RenderTransformOrigin="0.608,0.471" Grid.Row="1" Margin="16,0,6,0"/>
</DockPanel>
<TextBlock TextWrapping="Wrap" Text="111" Grid.Row="2" Grid.Column="0" Foreground="White" FontSize="10"/>
</Grid>
</Border>
</UserControl>
Начнем с того, что в WPF есть такой компонент, как Viewbox
, он автоматически меняет контент, который находится в нем. Viewbox
позволяет настраивать пропорции при помощи свойства Stretch
, допустим нам надо сделать квадрат, который внутри будет иметь некий текст, настраиваем все, делаем как надо, получаем, например такое:
<Border Background="Green" Width="100" Height="100">
<TextBlock Text="Текст"
VerticalAlignment="Center" TextAlignment="Center"
Foreground="White" FontSize="16"
Typography.Capitals="AllSmallCaps"/>
</Border>
Что даст нам предсказуемый результат, где размер будет статичный:
Помещаем это в Viewbox
и задаем Stretch="Uniform"
, разметка превращается в такое:
<Viewbox Stretch="Uniform">
<Border Background="Green" Width="100" Height="100">
<TextBlock Text="Текст"
VerticalAlignment="Center" TextAlignment="Center"
Foreground="White" FontSize="16"
Typography.Capitals="AllSmallCaps"/>
</Border>
</Viewbox>
Результатом уже будет квадрат, который меняет размер и сохраняет все пропорнции:
Имея все это, мы можем сделать уже допустим такое:
<UserControl.Style>
<Style TargetType="UserControl">
<Setter Property="Background">
<Setter.Value>
<LinearGradientBrush>
<GradientStop Color="#4e9e6d"/>
<GradientStop Color="#0e2806" Offset="1"/>
</LinearGradientBrush>
</Setter.Value>
</Setter>
<Setter Property="Foreground" Value="#f9fcfd"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="UserControl">
<Viewbox Stretch="Uniform">
<Border Background="{TemplateBinding Background}"
MinWidth="100" MinHeight="100"
Width="100" Height="100"
Padding="3">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Viewbox Grid.Row="1">
<TextBlock Text="{Binding Text, ElementName=uc, FallbackValue=Text}"
VerticalAlignment="Center" TextAlignment="Center"
Foreground="{TemplateBinding Foreground}"
Typography.Capitals="AllSmallCaps" />
</Viewbox>
<TextBlock Grid.Row="2" Text="{Binding Numb, ElementName=uc, FallbackValue=00}"
Foreground="{TemplateBinding Foreground}"
FontSize="10"/>
</Grid>
</Border>
</Viewbox>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</UserControl.Style>
И получим:
Вы спросите: "а зачем тут внутренний текст также обернут в Viewbox
?", а чтобы он органично вписывался в этот квадрат, если там будет больше одной буквы. Небольшая демонстрация:
Как видите, если использовать грамотно позиционирование объектов, а именно использовать разные *Alignment
свойства (допустим центральный текст у меня имеет VerticalAlignment="Center" TextAlignment="Center"
, что устанавливает вертикальный размер элемента строго по контенту, а горизонтальный растягивает на максимально допустимый размер предка, ну и TextAlignment
делает сам текст по середине блока) и Viewbox
, то любой контент без труда можно сделать динамически подстраиваемым.
если я правильно понял Вашу проблему, то Вам должна помочь такая разметка:
<WrapPanel Orientation="Horizontal" VerticalAlignment="Top" HorizontalAlignment="Stretch" ItemWidth="90">
<Grid Height="auto" Width="auto" Background="#FF58B26D" Margin="5, 5, 0, 5">
<Grid.RowDefinitions>
<RowDefinition Height="1*"/>
<RowDefinition Height="10*"/>
<RowDefinition Height="1*"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="1*"/>
<ColumnDefinition Width="20*"/>
<ColumnDefinition Width="1*"/>
</Grid.ColumnDefinitions>
<TextBlock Grid.Column="1"
Grid.Row="1"
VerticalAlignment="Center"
HorizontalAlignment="Center"
Foreground="White"
FontSize="35"
TextAlignment="Center">A</TextBlock>
<TextBlock Grid.Column="0"
Grid.Row="2"
Grid.ColumnSpan="3"
VerticalAlignment="Center"
HorizontalAlignment="Left"
Foreground="White"
FontSize="11"
TextAlignment="Center">11111</TextBlock>
</Grid>
</WrapPanel>
Вот так он выглядит:
Но здесь мы вынуждены контролировать ширину элемента, что бы при изменении текста, сам элемент не расползался и не сужался.
Как Вы можете заметить, я задаю значение для свойства ItemWidth = 90
, что бы контролировать ширину родительского объекта, так же вы можете задать MinWidth
для элемента что бы он не мог стать уже, но мог расшириться, что бы влез весь текст.
У меня есть 2 объекта один статичный другой подвижныйНужно чтобы статичный объект повторял положение подвижного
есть функция которая возвращает записи из базы IEnumerable<Persons>
Если бот общается с пользователем в лс, то при сообщении /commands , бот все норм создает такую клавиатуру, а если в групповом, то выдает ошибку...