WPF - Наилучшая практика для обычного управления [Метка: Входные данные]

StackOverflow https://stackoverflow.com/questions/1015226

  •  06-07-2019
  •  | 
  •  

Вопрос

Мне интересно, какой самый лучший и быстрый способ получить хорошо известную комбинацию ввода метки [или вывода, не имеет значения] в WPF.Это простая задача, просто подумайте о быстром выводе "объекта".:


Имя - Кристиан

Возраст - 28 лет

Настроение - Хорошее


Я знаю, я могу использовать сетку с текстовыми блоками.Но, честно говоря, "короткий" XAML для этого занимает почти половину страницы (определения строк, ColDefs, Grid.Col на каждой метке)

Альтернативный способ, использующий три панели стека (по горизонтали) с одной вертикальной, также кажется немного глупым.В этом случае я должен присвоить каждой метке фиксированную ширину, чтобы получить правильный отступ.И это просто "кажется" неправильным.

Итак, учитывая ситуацию выше, у вас есть пользовательский объект с 3-6 свойствами, которые вы просто хотите выгрузить в свой графический интерфейс как доступные только для чтения, как бы вы это сделали (в WPF, Silverlight тоже, если вы действительно в настроении :).

Я могу, конечно, написать usercontrol для этого.Но зачем изобретать велосипед, если он, возможно, уже есть...

И, наконец, чтобы проиллюстрировать еще больше, приведу пример, который я только что создал в реальной жизни и который послужил причиной для этого поста:

      <StackPanel>
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="Log Count"  Width="100"/>
            <TextBlock Text="{Binding LastLogRun.LogMessageCount}"/>
        </StackPanel>
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="Start Time" Width="100"/>
            <TextBlock Text="{Binding LastLogRun.StartTime}"/>
        </StackPanel>
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="End Time" Width="100"/>
            <TextBlock Text="{Binding LastLogRun.EndTime}"/>
        </StackPanel>
    </StackPanel>
Это было полезно?

Решение

Если вы используете 3.5sp1, вы можете использовать StringFormat в привязке. Нечто подобное должно работать ...

<TextBlock Text="{Binding LastLogRun.LogMessageCount, StringFormat={}Log Count - {0}}" />

Другие советы

Возможно, вам следует пересмотреть свой пользовательский интерфейс. Почему вы хотите, чтобы метка - текстовое поле находилась в одной строке? Это ужасная трата пространства.

Почему бы не пометить поверх texbox? Тогда у вас есть простой интерфейс и простой XAML:

<StackPanel Orientation="Vertical">
  <TextBlock>Name</TextBlock>
  <TextBox />
  <TextBlock>Age</TextBlock>
  <TextBox />
  <TextBlock>Mood</TextBlock>
  <TextBox />
</StackPanel>

Добавьте немного стилей для ваших текстовых блоков, и вы получите хороший, чистый пользовательский интерфейс с очень небольшим повторением.

Вы могли бы использовать общие группы размеров, чтобы получить поведение сетки автоматического определения размера двух красиво выровненных столбцов, сохраняя при этом возможность перенести сложность в UserControl.

Вот пример использования элемента управления LabeledEdit, который будет делать то, что вы ищете.Вся сложность была учтена в UserControl, и все, что вам нужно сделать, это не забыть установить Grid.IsSharedSizeScope на StackPanel:

<Window x:Class="WpfApplication5.Window1"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:WpfApplication5"
        Name="Self" Title="Window1" Height="300" Width="300">
    <StackPanel Grid.IsSharedSizeScope="True">
        <local:LabeledEdit Label="Name"/>
        <local:LabeledEdit Label="Age" Text="28"/>
        <!-- and with databinding... -->
        <local:LabeledEdit Label="Width"
                           Text="{Binding Width, ElementName=Self}"/>
        <local:LabeledEdit Label="Height"
                           Text="{Binding Height, ElementName=Self}"/>
    </StackPanel>
</Window>

И вот исходный код для UserControl.LabeledEdit.xaml:

<UserControl x:Class="WpfApplication5.LabeledEdit"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             Name="Self">
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="Auto" SharedSizeGroup="LabeledEdit_Labels"/>
            <ColumnDefinition Width="*"/>
        </Grid.ColumnDefinitions>
        <Label Grid.Column="0" Content="{Binding Label, ElementName=Self}"/>
        <TextBox Grid.Column="1" Text="{Binding Text, ElementName=Self}"/>
    </Grid>
</UserControl>

Помеченный как edit.xaml.cs:

using System.Windows;

namespace WpfApplication5
{
    public partial class LabeledEdit
    {
        public static readonly DependencyProperty LabelProperty =
            DependencyProperty.Register("Label", typeof(object), typeof(LabeledEdit));
        public static readonly DependencyProperty TextProperty =
            DependencyProperty.Register("Text", typeof(string), typeof(LabeledEdit),
            new FrameworkPropertyMetadata("", FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));

        public LabeledEdit()
        {
            InitializeComponent();
        }

        public object Label
        {
            get { return GetValue(LabelProperty); }
            set { SetValue(LabelProperty, value); }
        }
        public string Text
        {
            get { return (string)GetValue(TextProperty); }
            set { SetValue(TextProperty, value); }
        }
    }
}

набор инструментов silverlight имеет DataForm элемент управления, который работает довольно круто!

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top