在 Gridview 中使用复选框输入并将值插入 SQL 服务器数据库

Using a checkbox input in Gridview and inserting is value in to SQL Server database

我正在尝试在 gridview 中使用复选框控件。基本上,用户会输入项目描述、所用项目的数量,以及它是否已经“售出”库存。选中时的复选框将指示该项目已售出。未选中它可以为空或否。我可以将数据库中的值存储为 1/2、true/false、yes/no。没关系。

我试过在我的数据库中使用位类型、int 和 varchar。并尝试了多种方法来获取 C# 中的检查值,但似乎无法正常工作。

我到处搜索并找到了有关如何使用它来保存或删除多行的示例。但我需要它在我的数据库中实际存储一个值。

这是我从其他帖子中搜集的代码,几乎可以正常工作。

public partial class WebForm1 : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {
        if (!Page.IsPostBack)
        {
            SetInitialRow();
        }
    }

    private void SetInitialRow()
    {
        DataTable dt = new DataTable();
        DataRow dr = null;

        dt.Columns.Add(new DataColumn("RowNumber", typeof(string)));
        dt.Columns.Add(new DataColumn("Column1", typeof(string)));
        dt.Columns.Add(new DataColumn("Column2", typeof(string)));
        dt.Columns.Add(new DataColumn("Column3", typeof(string)));

        dr = dt.NewRow();

        dr["RowNumber"] = 1;
        dr["Column1"] = string.Empty;
        dr["Column2"] = string.Empty;
        dr["Column3"] = string.Empty;

        dt.Rows.Add(dr);

        ViewState["CurrentTable"] = dt;

        Gridview1.DataSource = dt;
        Gridview1.DataBind();
    }

    private void AddNewRowToGrid()
    {
        int rowIndex = 0;

        if (ViewState["CurrentTable"] != null)
        {
            DataTable dtCurrentTable = (DataTable)ViewState["CurrentTable"];
            DataRow drCurrentRow = null;

            if (dtCurrentTable.Rows.Count > 0)
            {
                for (int i = 1; i <= dtCurrentTable.Rows.Count; i++)
                {
                    TextBox itemDesc = (TextBox)Gridview1.Rows[rowIndex].Cells[1].FindControl("txtItemDesc");
                    TextBox quantity = (TextBox)Gridview1.Rows[rowIndex].Cells[2].FindControl("txtQuantity");
                    CheckBox sold = (CheckBox)Gridview1.Rows[rowIndex].Cells[3].FindControl("alreadySold");
                    drCurrentRow = dtCurrentTable.NewRow();
                    drCurrentRow["RowNumber"] = i + 1;
                    dtCurrentTable.Rows[i - 1]["Column1"] = itemDesc.Text;
                    dtCurrentTable.Rows[i - 1]["Column2"] = quantity.Text;
                    dtCurrentTable.Rows[i - 1]["Column3"] = sold.Checked.ToString();
                 
                    rowIndex++;
                }

                dtCurrentTable.Rows.Add(drCurrentRow);

                ViewState["CurrentTable"] = dtCurrentTable;

                Gridview1.DataSource = dtCurrentTable;
                Gridview1.DataBind();
            }
        }
        else
        {
            Response.Write("ViewState is null");
        }

        // Set Previous Data on Postbacks
        SetPreviousData();
    }

    private void SetPreviousData()
    {
        int rowIndex = 0;

        if (ViewState["CurrentTable"] != null)
        {
            DataTable dt = (DataTable)ViewState["CurrentTable"];

            if (dt.Rows.Count > 0)
            {
                for (int i = 0; i < dt.Rows.Count; i++)
                {
                    TextBox itemDesc = (TextBox)Gridview1.Rows[rowIndex].Cells[1].FindControl("txtItemDesc");
                    TextBox quantity = (TextBox)Gridview1.Rows[rowIndex].Cells[2].FindControl("txtQuantity");
                    CheckBox sold = (CheckBox)Gridview1.Rows[rowIndex].Cells[3].FindControl("alreadySold");

                    itemDesc.Text = dt.Rows[i]["Column1"].ToString();
                    quantity.Text = dt.Rows[i]["Column2"].ToString();
                    sold.Checked = dt.Rows[i]["Column3"].ToString().ToUpperInvariant() == "TRUE";

                    rowIndex++;
                }
            }
        }
    }

    protected void ButtonAdd_Click(object sender, EventArgs e)
    {
        AddNewRowToGrid();
    }

    protected void Save(object sender, System.EventArgs e)
    {
        if (ViewState["CurrentTable"] != null)
        {
            DataTable dt = new DataTable();
            dt = ViewState["CurrentTable"] as DataTable;

            if (dt.Rows.Count > 0)
            {
                using (SqlConnection con = new SqlConnection(ConfigurationManager.ConnectionStrings["constr"].ConnectionString))
                {
                    SqlCommand cmd = null;

                    foreach (GridViewRow row in Gridview1.Rows)
                    {
                        cmd = new SqlCommand("INSERT INTO SampleTest (ItemDesc, Quantity, Sold) VALUES (@Column1, @Column2, @Column3)", con);
                        string itemDesc = (row.FindControl("txtItemDesc") as TextBox).Text;
                        string quantity = (row.FindControl("txtQuantity") as TextBox).Text;
                        CheckBox sold = (row.FindControl("alreadySold") as CheckBox);

                        if (sold == null) 
                        {
                            sold.Checked = false;
                        }
                        else
                        {
                            sold.Checked = true;
                        }

                        cmd.Parameters.AddWithValue("@Column1", itemDesc);
                        cmd.Parameters.AddWithValue("@Column2", quantity);
                        cmd.Parameters.AddWithValue("@Column3", sold);

                        con.Open();
                        cmd.ExecuteNonQuery();
                        con.Close();
                    }

                    //cmd = new SqlCommand("SELECT Column1,Column2,Column3 FROM SampleTest", con);
                    //SqlDataAdapter da = new SqlDataAdapter(cmd);
                    //DataTable dt1 = new DataTable();
                    //da.Fill(dt1);
                    //this.gvSample.DataSource = dt1;
                    //this.gvSample.DataBind();
                }
            }
        }
    }
}

在你的存档中,而不是 CheckBox sold 试试这样的东西:

bool sold = (row.FindControl("alreadySold") as CheckBox)?.Checked ?? false;

所以对上面的内容做一点解释:

  1. 因为 CheckBox 可以 return null。
  2. '?'在复选框中)?是一个 null 条件检查,它将防止在它为 null 时抛出 null 异常。
  3. '??'是说如果前面的代码为 null,它不会分配 null,而是分配 'false'。现在如果 ?? 之前的代码不为 null,则它将 bool 变量值设置为 .Checked 实际是什么(真或假)。

现在,如果您的数据库允许在该列中使用 NULL,并且您对此没有意见,您还可以执行以下操作:

bool? sold = (row.FindControl("alreadySold") as CheckBox)?.Checked;

^布尔?是一种所谓的 Nullable 值类型。值类型不能为 null,但可为 null 的值类型环绕一个值类型并允许它为 null。

我是个白痴。谢谢B.O.B。用于解释空值和复选框控件发生了什么。它真的帮助我理解了正在发生的事情。其他事情不起作用的原因是因为我在 HTML 页面的复选框控件上有一个 type-o。一旦我确定一切正常。