简体   繁体   English

我有两个组合框和xml文件,我想从xml中填充组合框1中的服务器名称,并根据服务器名称填充第二个组合框

[英]i have two combo boxes and xml file, i want to populate server name in combo box 1 from xml and based on server name populate second combo box

XML : XML:

<?xml version="1.0" encoding="utf-8"?>

<servers>
    <server>s2
        <database>db1</database>
        <database>db2</database>    

    </server>

    <server>s3
        <database>db3</database>
        <database>db4</database>    

    </server>

</servers>

I want to get database based on server name & return as a list of string type. 我想基于服务器名称获取数据库并以字符串类型列表的形式返回。

view : 查看:

This function will take server name as a parameter from first combo box and based on the will filter database and populate second combobox 此函数将从第一个组合框中获取服务器名称作为参数,并基于将过滤数据库并填充第二个组合框的参数

public List<string> GetDatabases(string serv)
       {          
           var item = from items in xdoc.Descendants("database")
                      where (string)items.Element("server") == serv
                      select items.Elements("database").ToList();                        
           foreach (var items in item)
           {
               lstDBName.Add(items.ToString());
           }               
           return lstDBName;

       }

The XML you posted is not valid. 您发布的XML无效。 If you test it with an XML validator you will see it gives this error: 如果您使用XML验证程序对其进行测试,则会看到此错误消息:

Errors in the XML document: 
    1:  1   Content is not allowed in prolog.

You can easily fix it by adding an attribute to store server name like this: 您可以通过添加如下属性来轻松修复它:存储服务器名称,如下所示:

<?xml version="1.0" encoding="utf-8"?>
<servers>
    <server name="s2">
        <database>db1</database>
        <database>db2</database>    
    </server>
    <server name="s3">
        <database>db3</database>
        <database>db4</database>    
    </server>
</servers>

And you can modify (and simplify a bit) your code like this: 您可以像这样修改(并简化一点)您的代码:

public List<string> GetDatabases(string serv)
{
    XDocument xdoc = XDocument.Load("XMLFile1.xml");
    var lstDBName = (from items in xdoc.Descendants("server")
                     where items.Attribute("name").Value == serv
                     from item in items.Elements("database")
                     select item.Value)
                     .ToList();
    return lstDBName;
}

I read the XML inside the method from a file called XMLFile1.xml, you can change that bit with however you're reading the XML. 我从一个名为XMLFile1.xml的文件中读取了方法内部的XML,但是可以在读取XML的同时更改该位。

This code sample would return a list of two strings with values "db1" and "db2" as expected 此代码示例将按预期返回两个字符串的列表,其值分别为“ db1”和“ db2”

As I can understand, you need some mechanism which on selection in first combo will update the second combo with first combo related data (based on your question name: 据我了解,您需要某种机制,在第一个组合中进行选择时,将使用与第一个组合相关的数据来更新第二个组合(根据您的问题名称:

i have two combo boxes and xml file, i want to populate server name in combo box 1 from xml and based on server name populate second combo box 我有两个组合框和xml文件,我想从xml中填充组合框1中的服务器名称,并根据服务器名称填充第二个组合框

). )。

Here is a solution which is based on two observable collections an its update mechanisms. 这是一个基于两个可观察集合及其更新机制的解决方案。 1. Xaml code: 1. Xaml代码:

<Window x:Class="SimpleDataGrid.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:simpleDataGrid="clr-namespace:SimpleDataGrid"
    Title="MainWindow" Height="350" Width="525">
<Window.DataContext>
    <simpleDataGrid:GridViewModel/>
</Window.DataContext>
<Grid >
    <DataGrid x:Name="SelectDataGrid" ItemsSource="{Binding Persons}" HorizontalAlignment="Left" VerticalAlignment="Top" AutoGenerateColumns="False">
        <DataGrid.Columns>
            <DataGridCheckBoxColumn x:Name="dgCheckBox" Header="Select" Width="45" Binding="{Binding IsChecked}"/>
            <DataGridTextColumn Header="FIRST NAME" Width="125" Binding="{Binding FNAME}"/>
            <DataGridTextColumn Header="LAST NAME" Width="125" Binding="{Binding LNAME}"/>
            <DataGridComboBoxColumn Header="Servers"
                                    DisplayMemberPath="ServerName" SelectedValueBinding="{Binding SelectedServer, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}">
                <DataGridComboBoxColumn.ElementStyle>
                    <Style TargetType="ComboBox">
                        <Setter Property="ItemsSource" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}, Path=DataContext.Servers}"/>
                        <Setter Property="IsReadOnly" Value="True"/>
                    </Style>
                </DataGridComboBoxColumn.ElementStyle>
                <DataGridComboBoxColumn.EditingElementStyle>
                    <Style TargetType="ComboBox">
                        <Setter Property="ItemsSource" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}, Path=DataContext.Servers}"/>
                    </Style>
                </DataGridComboBoxColumn.EditingElementStyle>
            </DataGridComboBoxColumn>
            <DataGridComboBoxColumn Header="Dbs" 
                                    DisplayMemberPath="DbName" 
                                    SelectedValueBinding="{Binding SelectedDb, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}">
                <DataGridComboBoxColumn.ElementStyle>
                    <Style TargetType="ComboBox">
                        <Setter Property="ItemsSource" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}, Path=DataContext.Dbs}"/>
                        <Setter Property="IsReadOnly" Value="True"/>
                    </Style>
                </DataGridComboBoxColumn.ElementStyle>
                <DataGridComboBoxColumn.EditingElementStyle>
                    <Style TargetType="ComboBox">
                        <Setter Property="ItemsSource" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridCell}}, Path=DataContext.Dbs}"/>
                    </Style>
                </DataGridComboBoxColumn.EditingElementStyle>
            </DataGridComboBoxColumn>
        </DataGrid.Columns>
    </DataGrid>
</Grid></Window>

2. Main Model Code which gives the solution.The UpdateDbCollection method can call your GetDatabases method, query server related data bases, put that data to the 'newDbs' list and update the second combo observable collections with new data in way when it add a new data and remode an old data. 2.提供解决方案的主模型代码。UpdateDbCollection方法可以调用GetDatabases方法,查询与服务器相关的数据库,将该数据放入“ newDbs”列表,并在添加新数据时以新数据方式更新第二个组合可观察集合。 数据并重新设置数据。

    public class Person : BaseObservableObject
{
    private string _lName;
    private string _fName;
    private bool _checked;

    private object _selectedServer;
    private DbDetails _selectedDb;

    public Person()
    {
        Dbs = new ObservableCollection<DbDetails>();
        Servers = new ObservableCollection<ServerDetails>(new List<ServerDetails>
        {
            new ServerDetails
            {
                ServerName = "A",
                DbDetailses = new List<DbDetails>
                {
                    new DbDetails{DbName = "AA"},
                    new DbDetails{DbName = "AB"},
                    new DbDetails{DbName = "AC"},
                }
            },
             new ServerDetails
            {
                ServerName = "B",
                DbDetailses = new List<DbDetails>
                {
                    new DbDetails{DbName = "BA"},
                    new DbDetails{DbName = "BB"},
                    new DbDetails{DbName = "BC"},
                }
            },
             new ServerDetails
            {
                ServerName = "C",
                DbDetailses = new List<DbDetails>
                {
                    new DbDetails{DbName = "CA"},
                    new DbDetails{DbName = "CB"},
                }
            }
        });
    }
    public DbDetails SelectedDb
    {
        get { return _selectedDb; }
        set
        {
            _selectedDb = value;
            OnPropertyChanged();
        }
    }

    public object SelectedServer
    {
        get { return _selectedServer; }
        set
        {
            _selectedServer = value;
            OnPropertyChanged();
            UpdateDbCollection(SelectedServer as ServerDetails);
        }
    }

    private void UpdateDbCollection(ServerDetails serverDetails)
    {
        //here you can get your db details by selected server
        var newDbs = serverDetails.DbDetailses;
        newDbs.ForEach(details => Dbs.Add(details));
        var valuesToClear =
            Dbs.Where(
                existingDbDetails => newDbs.FirstOrDefault(dbDetails => existingDbDetails == dbDetails) == null).ToList();
        valuesToClear.ForEach(details => Dbs.Remove(details));
    }

    public ObservableCollection<ServerDetails> Servers { get; set; }

    public ObservableCollection<DbDetails> Dbs { get; set; }

    public bool IsChecked
    {
        get { return _checked; }
        set
        {
            _checked = value;
            OnPropertyChanged();
        }
    }

    public string LNAME
    {
        get { return _lName; }
        set
        {
            _lName = value;
            OnPropertyChanged();
        }
    }

    public string FNAME
    {
        get { return _fName; }
        set
        {
            _fName = value;
            OnPropertyChanged();
        }
    }
}                                                

3. Models: 3.型号:

    public class ServerDetails:BaseObservableObject
{
    private string _serverName;

    public string ServerName
    {
        get { return _serverName; }
        set
        {
            _serverName = value;
            OnPropertyChanged();
        }
    }

    public List<DbDetails> DbDetailses { get; set; }
}

public class DbDetails:BaseObservableObject
{
    private string _dbName;

    public string DbName
    {
        get { return _dbName; }
        set
        {
            _dbName = value;
            OnPropertyChanged();
        }
    }
}
  1. View model code: 查看模型代码:

    public class GridViewModel:BaseObservableObject { 公共类GridViewModel:BaseObservableObject {

     public GridViewModel() { var l = new List<Person> { new Person {FNAME = "John", LNAME = "W"}, new Person {FNAME = "George", LNAME = "R"}, new Person {FNAME = "Jimmy", LNAME = "B"}, new Person {FNAME = "Marry", LNAME = "B"}, new Person {FNAME = "Ayalot", LNAME = "A"}, }; Persons = new ObservableCollection<Person>(l); } public ObservableCollection<Person> Persons { get; set; } 

    } }

  2. BaseObservableObject is a simple implementation of INotifyPropertyChanged. BaseObservableObject是INotifyPropertyChanged的简单实现。

I hope it will help you. 希望对您有帮助。 Thanks an regards, 感谢您的问候,

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM