Программная привязка списка не работает в WPF - PullRequest
0 голосов
/ 12 сентября 2011

У меня есть пользовательский элемент управления, который программно устанавливает источник данных списка (точнее, XmlDataProvider и DataTemplate), но во время выполнения он никогда не отображается должным образом.Когда пользовательский элемент управления загружен.Все настройки для провайдеров данных не отражаются.

Можете ли вы помочь мне с этим?Я действительно новичок в разработке приложений WPF.

TIA

Вот код:

XAML

<UserControl x:Class="ENGAGIAUCL.Views.ImageViewer"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Height="500" Width="550">
    <UserControl.Resources>
        <XmlDataProvider x:Key="FormDataProvider"/>
        <DataTemplate x:Key="FormTemplate">
            <Border Background="#2200FF00"
                    BorderBrush="Black" 
                    BorderThickness="1"
                    CornerRadius="8"  
                    Margin="2,4,2,4" 
                    Padding="4">
                <StackPanel HorizontalAlignment="Stretch">
                    <TextBlock Text="{Binding XPath=name}" />
                </StackPanel>
            </Border>
        </DataTemplate>
    </UserControl.Resources>
    <DockPanel>
        <Border DockPanel.Dock="Top"
                Height="45">
            <TextBlock x:Name="tbkContentTitle"
                       Text="Content Title Goes Here" 
                       VerticalAlignment="Center" 
                       HorizontalAlignment="Center"
                       FontSize="20">
            </TextBlock>
        </Border>
        <DockPanel>
            <Border DockPanel.Dock="Bottom">
            </Border>
            <Grid>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="150"/>
                    <ColumnDefinition/>
                </Grid.ColumnDefinitions>
                <ListBox x:Name="lbPreview" 
                     IsSynchronizedWithCurrentItem="True"
                     VerticalAlignment="Top" 
                     Height="455" 
                     Grid.Column="0"
                     ItemsSource="{Binding}">
                </ListBox>
                <Frame x:Name="ActualContentFrame" 
                                           Grid.Column="1"
                       Source="{Binding XPath=url}">
                </Frame>
            </Grid>
        </DockPanel>
    </DockPanel>
</UserControl>

А вот файл .cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Xml;

using EngagiaCL.CommonObjects;
using EngagiaCL.Functions;

namespace ENGAGIAUCL.Views
{
    /// <summary>
    /// Interaction logic for ImageViewer.xaml
    /// </summary>
    public partial class ImageViewer : UserControl
    {
        public ImageViewer()
        {
            InitializeComponent();
            Loaded += (s, e) =>
                {
                    LoadContents();
                };
        }

        #region Methods
        private void LoadContents()
        {
            if (CurrentUser != null)
            {
                XmlDataProvider provider = (XmlDataProvider)this.FindResource("FormDataProvider");
                DataTemplate template = (DataTemplate)this.FindResource("FormTemplate");
                Binding templatebinding = new Binding();

                provider.Document = CurrentUser.UserDoc;
                provider.XPath = GetResourcePath();

                template.DataType = (object)GetDataTemplateObject();
                Resources["FormDataProvider"] = provider;
                Resources["FormTemplate"] = template;
            }
        }
        private string GetResourcePath()
        {
            string path = string.Empty;

            if (ContentType == "ADMIN")
            {
                path = "/SyncLoginResponse/AdminForms/AdminForm";
            }
            else
            {
                path = "/SyncLoginResponse/Forms/Form";
            }

            return path;
        }
        private string GetDataTemplateObject()
        {
            string templateobject = string.Empty;

            if (ContentType == "ADMIN")
            {
                templateobject = "AdminForm";
            }
            else
            {
                templateobject = "Form";
            }

            return templateobject;
        }
        #endregion

        #region Properties
        public UserInformation CurrentUser { get; set; }
        public string ContentType { get; set; }
        #endregion
    }
}

А вот для справки xml:

</SyncLoginResponse>
    <AdminForms>
        <AdminForm>
            <name>Best Form Ever/html</name>
            <url>
                http://blahblahblah/
            </url>
        </AdminForm>
    </AdminForms>
</SyncLoginResponse>

На что следует обратить внимание:

  1. CurrentUser - это объект, содержащий документ xml в UserDoc.свойство.
  2. Большинство из того, что я сделал в этом приложении, - это кусочки того, что я понял в поиске, так что будьте добры терпеть меня.

1 Ответ

0 голосов
/ 12 сентября 2011

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

  1. Ваш ListBox.ItemsSource связан как {Binding}, то есть привязан к DataContext всего представления, но нигде в вашем коде нет, вы установили DataContext представления или любого родительского элемента более высокого уровня для ListBox.

  2. Ваша переменная templateBinding из кода не используется нигде после создания.

  3. Почему вы устанавливаете FormDataProvider и FormTemplate снова в конце вашего LoadContents метода? Если вы хотите «обновить» свой словарь Resources, то это не правильный путь.

Для обновления Resources вам необходимо удалить и добавить ресурсы в свой словарь Resources и одновременно использовать DynamicResource ссылку на разметку.

Дайте мне знать, чего именно вы хотите достичь.

...