【问题标题】:How to add a new row or delete one in DataBase from DataGrid如何从 DataGrid 在数据库中添加新行或删除行
【发布时间】:2016-11-23 12:04:08
【问题描述】:

所以我在WPF 中有这个学校项目,我必须将DataGrid 绑定到SQLite DataBase。在XAML 我还有3 个buttonsLoad(加载表格)、UpdateCancel(取消所有更改并直接从ObservableCollection 重新加载DataGrid。 我在这里有XAML 行:

<DataGrid x:Name="dataGrid" AutoGenerateColumns="True" Canvas.Left="10" Canvas.Top="10" AlternatingRowBackground="LightGreen" Height="245" Width="500" ItemsSource="{Binding Userss.UserCol, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" DataContext="{Binding RelativeSource={RelativeSource Self}}"/>

我有一个UserssClass,在那里我创建了我的ObservableCollection,用于存储来自我的SQLitedatabase 的数据。

public class Userss : INotifyPropertyChanged
{
    public static SQLiteConnection m_dd = new SQLiteConnection("Data Source=MyDatabase.sqlite;Version=3;");

    private static ObservableCollection<Userss> userCol = new ObservableCollection<Userss>();

    public ObservableCollection<Userss> UserCol
    {
        get { return userCol; }
        set
        {
            userCol = value;
            RaisePropertyChanged();
        }
    }

    public int Id { get; set; }
    private string _name;
    public string Name
    {
        get { return _name; }
        set
        {
            _name = value;
            RaisePropertyChanged();
        }
    }

    private Sex _sex;
    public Sex Sex
    {
        get { return _sex; }
        set
        {
            _sex = value;
            RaisePropertyChanged();
        }
    }

    private Stations _station;
    public Stations Station
    {
        get { return _station; }
        set
        {
            _station = value;
            RaisePropertyChanged();
        }
    }

    private Jobs _job;
    public Jobs Job
    {
        get { return _job; }
        set
        {
            _job = value;
            RaisePropertyChanged();
        }
    }

    private DateTime _date;
    public DateTime Date
    {
        get { return _date; }
        set
        {
            _date = value;
            RaisePropertyChanged();
        }
    }

    public static ObservableCollection<Userss> GetValues()
    {
        m_dd.Open();
        string sql = "select id,name,sex,station,job,date from user";
        userCol.Clear();
        SQLiteCommand cmd = new SQLiteCommand(sql, m_dd);
        SQLiteDataReader reader = cmd.ExecuteReader();
        while (reader.Read())
        {
            string sex1 = reader["sex"].ToString();
            string station1 = reader["station"].ToString();
            string job1 = reader["job"].ToString();
            string data1 = reader["date"].ToString();
            userCol.Add(new Userss()
            {
                Id = Convert.ToInt32(reader["id"]),
                Name = reader["name"].ToString(),
                Sex = (Sex)Enum.Parse(typeof(Sex), sex1),
                Station = (Stations)Enum.Parse(typeof(Stations), station1),
                Job = (Jobs)Enum.Parse(typeof(Jobs), job1),
                Date = Convert.ToDateTime(data1)
            });
        }
        m_dd.Close();
        return userCol;
    }

    public event PropertyChangedEventHandler PropertyChanged;

    private void RaisePropertyChanged([CallerMemberName] string caller = "")
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(caller));
        }
    }
}

public enum Sex
{
    Male,
    Female
}
public enum Jobs
{
    Programmer,
    Designer,
    Manager,
    CTO,
    CEO,
}
public enum Stations
{
    Desktop,
    Laptop,
    Tablet
}}

这是我对 MainWindow 的实现

public partial class MainWindow : Window
{
    public SQLiteConnection m_db = new SQLiteConnection("Data Source=MyDatabase.sqlite;Version=3;");
    ObservableCollection<Userss> usersCollection = Userss.GetValues();
    public MainWindow()
    {
        InitializeComponent();
    }
    private void LoadButton_Click(object sender, RoutedEventArgs e)
    {
        try
        {
            dataGrid.ItemsSource = Userss.GetValues();

        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.ToString());
        }
    }

    private void Update_Click(object sender, RoutedEventArgs e)
    {
        if (MessageBox.Show("Are you sure you want to make those changes?", "Please confirm", MessageBoxButton.YesNo) == MessageBoxResult.Yes)
        {
            try
            {
                m_db.Open();
                foreach (var user in usersCollection)
                {
                    string sql = "UPDATE user SET Name = @name, Sex = @sex, Station = @station, Job = @job, Date = @date WHERE Id = @id";
                    SQLiteCommand command = new SQLiteCommand(sql, m_db);
                    command.Parameters.Add(new SQLiteParameter("@name", user.Name));
                    command.Parameters.Add(new SQLiteParameter("@sex", user.Sex.ToString()));
                    command.Parameters.Add(new SQLiteParameter("@station", user.Station.ToString()));
                    command.Parameters.Add(new SQLiteParameter("@job", user.Job.ToString()));
                    command.Parameters.Add(new SQLiteParameter("@date", user.Date.ToString()));
                    command.Parameters.Add(new SQLiteParameter("@id", user.Id.ToString()));
                    command.ExecuteNonQuery();
                }
                m_db.Close();
                usersCollection = Userss.GetValues();
                dataGrid.Items.Refresh();
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
        else
            this.dataGrid.CancelEdit();
    }

    private void CancelClick(object sender, RoutedEventArgs e)
    {
        if (MessageBox.Show("Are you sure you want to cancel those changes?", "Please confirm", MessageBoxButton.YesNo) == MessageBoxResult.Yes)
        {
            dataGrid.ItemsSource = Userss.GetValues();
        }
        else
            this.dataGrid.CancelEdit();
    }
}

我遇到的问题是,当我按下 Update Button 时,我更改的值会在 database 中更新,但如果我尝试删除或添加一行,则不会发生更新在database。 注意:我尝试过使用DataSetsAdapters,但没有成功(我相信是因为我将ComboBoxes 放入了DataGrid。 有什么想法可以在我的代码中更改吗?

【问题讨论】:

    标签: c# wpf sqlite data-binding datagrid


    【解决方案1】:

    您必须在 DataGrid 中实现特定事件。 例如:

    <DataGrid ItemsSource="{Binding Userss.UserCol, Mode=TwoWay, 
              UpdateSourceTrigger=PropertyChanged}"
              DataContext="{Binding RelativeSource={RelativeSource Self}}"
              RowEditEnding="DataGrid_RowEditEnding">
    

    所以在你的代码后面:

    private void DataGrid_RowEditEnding(object sender, DataGridRowEditEndingEventArgs e)
    {
        // Only act on Commit
        if (e.EditAction == DataGridEditAction.Commit)
        {
            //execute your update SQL
        }
    }
    

    对于删除很相似:

    将此添加到 xlmns:

    xmlns:ic="clr-namespace:System.Windows.Input;assembly=PresentationCore" 
    

    所以在你的数据网格中:

    <DataGrid 
        ItemsSource="{Binding Userss.UserCol, Mode=TwoWay, 
                         UpdateSourceTrigger=PropertyChanged}"
            DataContext="{Binding RelativeSource={RelativeSource Self}}"
            RowEditEnding="DataGrid_RowEditEnding"
            ic:CommandManager.PreviewExecuted="DataGrid_OnPreviewExecuted">
    

    在代码隐藏中:

    private void DataGrid_OnPreviewExecuted(object sender, ExecutedRoutedEventArgs e)
    {
        if (e.Command == DataGrid.DeleteCommand)
        {
            // Show MessageBox and get result
            if (result == No)
            {
                // Cancel Delete command by setting Handled = true
                e.Handled = true;
            }
            else
            {
                // execute you delete SQL       
            }
        }
    }
    

    【讨论】:

    • 我之前尝试过RowEditEnding,但没有成功。现在也不行了。我按回车后更改的数据从database返回到它们的初始值...
    【解决方案2】:

    您只提供更新数据库中数据的更新命令,而不提供插入和删除命令。尝试以同样的方式使用 SQLiteDataAdapter:

            adapter = new SQLiteDataAdapter();
    
            selcmd = new SQLiteCommand();
            selcmd.CommandText = "...";
            adapter.SelectCommand = selcmd;
    
            upcmd = new SQLiteCommand();
            upcmd.CommandText = "...";
            adapter.UpdateCommand = upcmd;
    
            delcmd = new SQLiteCommand();
            delcmd.CommandText = "...";
            adapter.DeleteCommand = delcmd;
    
            inscmd = new SQLiteCommand();
            inscmd.CommandText = "...";
            adapter.InsertCommand = inscmd;
    

    【讨论】:

    • 另外你必须使用连接、事务、数据表:)
    • 使用DataGrid的事件是坏学校成绩的坏方法
    • 你也可以在没有类的情况下决定这个任务,使用datagrid作为数据存储来存储数据库中的数据
    • 好的,但是我如何从DataGrid 中获取 ID?我看到你放了一个selcmd 我相信我可以这样使用它,但你能告诉我怎么用吗?
    猜你喜欢
    • 2012-02-11
    • 2010-12-18
    • 1970-01-01
    • 1970-01-01
    • 2012-07-24
    • 2021-06-09
    • 2014-07-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多