16, C# tabular data control

Posted by ultraviolet_998 on Wed, 02 Mar 2022 15:53:57 +0100

Initial DataGridView

  • The DataGridView control provides a powerful and flexible way to display data in tabular form. Users can use the DataGridView control to display a read-only view of a small amount of data, or they can align and zoom to display a markable view of a large dataset.
  • There are many ways to extend the DataView control. For example, you can programmatically specify your own sorting algorithm to create your own cell type. By selecting some properties, you can easily customize the appearance of the DataGridView control: you can store many types of data as data sources; you can also operate the DataGridView control without binding data sources.
  • Configure data source









Only fields are displayed before operation, and specific data are displayed after operation

Common properties


2. Data binding method

  • The Data Grid view control is used to display data from a variety of external data sources. Users can add rows and columns in this space and fill in the data.
  • To make the DataGrideView display the data in the database, you only need to bind this control to the data yard of the substitute database, and then you can automatically generate columns based on the schema of the data source.
  • There are two methods of binding mode:
    • Binding mode: bind the data in the existing database to the space
    • Unbound mode: manually populating data with code

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Data.SqlClient;

namespace _2_DataGridView Bind data source
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            dgvbindMode.DataSource = BindModSource().Tables[0];
            dgvNonbindMode.DataSource = NonBindSource();
        }
        private DataSet BindModSource()   //Binding mode, threaded database
        {
            string constr = "Server=.;user=sa;pwd=darly;database=csharpzx";
            SqlConnection mycon = new SqlConnection(constr);
            DataSet myds = new DataSet();
            try
            {
                mycon.Open();
                string sql = "select name,gender from mytable";
                SqlDataAdapter myda = new SqlDataAdapter(sql, mycon);
                myda.Fill(myds, "mytable");

            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message.ToString(), "Error prompt");

            }
            finally
            {
                mycon.Close();
            }
            return myds;
        }
        private DataTable NonBindSource()   //Unbound mode, no database
        {
            DataTable mydt = new DataTable();
            mydt.Columns.Add("name", Type.GetType("System.String"));
            mydt.Columns.Add("gender", Type.GetType("System.String"));
            string[,] mystr = { { "Zhang San", "female" }, { "Li Si", "female" }, { "Wang Wu", "female" }, { "Zhao Liu", "female" }, { "Zhang Qi", "female" }};
            for (int i = 0; i < mystr.Length / 2; i++)
            {
                DataRow myRow = mydt.NewRow();
                myRow[0] = mystr[i, 0];
                myRow[1] = mystr[i, 1];
                mydt.Rows.Add(myRow);

            }
            return mydt;
        }
    }
}

3. Get current cell

  • The current cell in the DataGridView control is obtained through the indexes of the Rows property and the Columb property of the DataGridView. Their indexes start from 0.

Instance, when clicking a cell, get the row and column you clicked, and get the value in the cell


using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace _3_Get cell
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet1.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet1.mytable);

        }

        //In the definition of the method, the first parameter sender refers to the control of the current operation, and the second parameter is used to return the content value of the control of the current operation
        private void dataGridView1_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            //Get row column index
            //1 way
            //int row = e.RowIndex + 1;   // The number of rows obtained;
            //int col = e.ColumnIndex + 1;   // Get the number of columns

            //MessageBox.Show("what you click is: row" + row.ToString() + "and column" + col.ToString() + ");
            //Mode 2

            //int row2 = dataGridView1.CurrentCell.RowIndex + 1;
            //int col2 = dataGridView1.CurrentCell.ColumnIndex + 1;
            //MessageBox.Show("what you click is: line" + row2.ToString() + "line" + col2 Tostring() + "column.";

            //Mode in Section 3

            //int row3 = dataGridView1.CurrentCellAddress.Y + 1;
            int col3 = dataGridView1.CurrentCellAddress.X + 1;

            //MessageBox.Show("what you click is: line" + row3.ToString() + "line" + col3 Tostring() + "column.";

            //The fourth way
            int row4 = dataGridView1.CurrentRow.Index + 1;   //This method applies only to rows, not columns.


            //Get cell content Value
            //The first way
            //string cell = dataGridView1.Rows[row4-1].Cells[col3-1].Value.ToString();

            //The second way
            string cell = dataGridView1.CurrentCell.Value.ToString();
            MessageBox.Show("What you click is: No" + row4.ToString() + "OK, page" + col3.ToString() + "Columns.\n The content is:"+cell);

        }
    }
}

4. DataGridView hides rows and columns

Hide and show
visible: true is displayed, false is hidden
Rows: row
Columns: columns

using System;
using System.Windows.Forms;

namespace _4_DataGridView Hide and show rows and columns
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);

        }

        private void button1_Click(object sender, EventArgs e)
        {
            string mystr = button1.Text;
            if (mystr.Contains("hide"))
            {
                //Gets the column in which the cell is located
                //int col = dataGridView1.CurrentCell.ColumnIndex;
                dataGridView1.Columns[4].Visible = false;
                button1.Text = "Show Department columns";
            }
            else
            {
                dataGridView1.Columns[4].Visible = true;
                button1.Text = "Hide Department column";
            }
        }

        private void button2_Click(object sender, EventArgs e)
        {
            string mystr = button2.Text;
            if (mystr.Contains("hide"))
            {
                dataGridView1.Rows[1].Visible = false;
                button2.Text = "Display three lines";
            }
            else
            {
                dataGridView1.Rows[1].Visible = true;
                button2.Text = "Hide Zhang Sanxing";
            }
        }
    }
}

5. Right click DataGridView to delete rows

Right click: ContextMenuStrip
Delete row datagridview1 Rows. Removeat (row index value);

using System;
using System.Windows.Forms;

namespace DataGrideView Right click Delete row
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);

        }
        private int rowIndex = 0;
        private void dataGridView1_CellMouseUp(object sender, DataGridViewCellMouseEventArgs e)
        {
            if (e.Button == MouseButtons.Right) //Determine whether the mouse operation event is left or right
            {
                this.dataGridView1.Rows[e.RowIndex].Selected = true;    //select line 
                //If there is no following command, each click will accumulate the selection, and multiple line records will be selected. The following command is to right-click to define that cell as the current cell;
                this.dataGridView1.CurrentCell = this.dataGridView1.Rows[e.RowIndex].Cells[0];
                rowIndex = e.RowIndex;  //Assign the index value of the current row to the public variable to judge whether it is an empty row (new row) when deleting
                //this.contextMenuStrip1.Show(this.dataGridView1, e.Location);   // The first parameter specifies the control, and the second parameter is where the current event occurs
                this.contextMenuStrip1.Show(Cursor.Position);  //Click the mouse to display

            }
        }

        private void Delete row ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            if (!this.dataGridView1.Rows[rowIndex].IsNewRow)
            {
                this.dataGridView1.Rows.RemoveAt(rowIndex);
            }
        }
    }
}

6. DataGridView sorting and filtering

Category: Sort
Filtering: change the DataSource by declaring the DataView,

using System;
using System.ComponentModel;
using System.Data;
using System.Windows.Forms;

namespace _6__DataGridView Ascending and filtering
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);

        }

        private void button1_Click(object sender, EventArgs e)
        {
            dataGridView1.Sort(dataGridView1.Columns[3], ListSortDirection.Ascending);  //The first parameter is based on which column beats, and the second parameter is Ascending or Descending: Descending descending, Ascending
        }

        private void button2_Click(object sender, EventArgs e)
        {
            //Parameter 1 source data table, parameter 2 filter criteria, parameter 3 arrangement method after filtering, parameter 4 status of current row (the status of dataview is specified as the status of current row)
            DataView dv = new DataView(this.csharpzxDataSet.mytable, "department='Development Department'", "age Asc", DataViewRowState.CurrentRows);
            //The above statement can be simply understood to filter the source data. The following statement binds the filtered data to the DataGridView.
            dataGridView1.DataSource = dv;
        }
    }
}

7. DataGridView directly modifies data

  • How to enter editing mode for DataGridView cells:
    • Double click or F12;
    • EditCellonEnter property is True. Configure DataGridView. When the user moves to this cell, the cell will switch to edit mode.
    • ESC cancels editing. If the EditCellOnEnter property is set to True, the cell will remain in edit mode, but all changes will be discarded. To commit changes, the user simply moves to a new cell or switches focus to another control.
  • To prevent cells from being edited, you can set
  • ReadOnly property of DataGridViewCell, DataGridViewColumn, datagridviewrow or DataGridView (region and content to be changed by the user)
  • To modify data in the datagridvive control, you can do so through the CellValueChanged event
using System;
using System.Data;
using System.Windows.Forms;
using System.Data.SqlClient;

namespace _7_DataGridView Modify data directly
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        private SqlConnection GeConnection()
        {
            string constr = "Server=.;user=sa;pwd=darly;database=csharpzx";
            SqlConnection mycon = new SqlConnection(constr);
            return mycon;
        }
        private void dgvBind()
        {
            SqlConnection mycon = GeConnection();
            try
            {
                mycon.Open();
                SqlDataAdapter sda =new  SqlDataAdapter("select * from mytable", mycon);
                DataTable table = new DataTable();
                sda.Fill(table);
                this.dataGridView1.AutoGenerateColumns = true;  //Set DataGridView to automatically create columns
                this.dataGridView1.DataSource = table;

                this.dataGridView1.EditMode = DataGridViewEditMode.EditOnEnter;

            }
            catch(Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
            finally
            {
                mycon.Close();

            }

        }

        private void Form1_Load(object sender, EventArgs e)
        {
            dgvBind();
        }

        private void dataGridView1_CellValueChanged(object sender, DataGridViewCellEventArgs e)
        {
            SqlConnection mycon = GeConnection();
            try
            {
                mycon.Open();

                string mystr1=dataGridView1.Columns[e.ColumnIndex].HeaderText+"="+"'"+dataGridView1.CurrentCell.Value.ToString()+"'";  //Gets the header of the column in which the cell before the file is located

                string mystr2=dataGridView1.Rows[e.RowIndex].Cells[0].Value.ToString();

                string updatsql = "update mytable set "+mystr1+" where id = "+mystr2;
                MessageBox.Show(updatsql);
                SqlCommand mycom = new SqlCommand(updatsql, mycon);
                mycom.ExecuteNonQuery();
                dgvBind();


            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
            finally
            {
                mycon.Close();

            }
        }
    }
}

8. The current row of DataGridView displays different colors

If you want the rows of the selected DataGridView to display different colors, you need to reset the selected DefaultCellStyle property in the RowPrePaint event of the DataGridView control

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace _8_DataGridView The current line displays different colors
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);

        }

        private void dataGridView1_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
        {
           
            if (e.RowIndex >= dataGridView1.Rows.Count - 1) return;  //If the selected line is a new line (content to be added), do not operate and return directly
            Color oldForeColor = new Color();
            Color oldBackColor = new Color();
            // object is the base class of all classes. Var can be all variable types. When the variable type is unknown, it can be declared in var format
             
            var row = dataGridView1.Rows[e.RowIndex];    //Line of action
            if (row == dataGridView1.CurrentRow)   //Judge whether the operation line is the same as the current line. If it is the same, it represents the first operation, so different styles should be drawn
            {
                if (row.DefaultCellStyle.ForeColor != Color.White) ;
                {
                    oldForeColor = row.DefaultCellStyle.ForeColor;  // Store the current foreground color
                    row.DefaultCellStyle.ForeColor = Color.White;   // Set the foreground color to white
                }
                if (row.DefaultCellStyle.BackColor != Color.Blue)
                {
                    oldBackColor = row.DefaultCellStyle.BackColor;
                    row.DefaultCellStyle.BackColor = Color.Blue;
                }
            }
            else
            {
                row.DefaultCellStyle.ForeColor = oldForeColor;
                row.DefaultCellStyle.BackColor = oldBackColor;
            }

        }
    }
}

9. DataGridView draws line numbers

Draw the row sequence number of the DataGridView
RowPostPaint event (the event executed after we finish painting the DataGridView), through the rectangular area of the Rectangle object, and then draw the serial number through the DrawText method of TextRenderer
Rectangle(x,y,width,height)
DrawText(IDeviceContext dc, text,font,Rectangle bounds, foreColor,TextFormatFlags) on which control is the first parameter (IDeviceContext dc) drawn, Rectangle bounds, rectangle borders, TextFormatFlags font alignment

using System;
using System.Drawing;
using System.Windows.Forms;

namespace _9_DataGridView Add line sequence number
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);

        }

        private void dataGridView1_RowPostPaint(object sender, DataGridViewRowPostPaintEventArgs e)
        {
            //e stands for DataGridView, and row of RowBound control
            Rectangle myrec = new Rectangle(e.RowBounds.Location.X, e.RowBounds.Location.Y, dataGridView1.RowHeadersWidth-5, e.RowBounds.Height);   //The width value is reduced to space the content from the next column
            TextRenderer.DrawText(e.Graphics, (e.RowIndex + 1).ToString(), dataGridView1.RowHeadersDefaultCellStyle.Font, myrec, dataGridView1.RowHeadersDefaultCellStyle.ForeColor, TextFormatFlags.VerticalCenter | TextFormatFlags.Right);
        }
    }
}

10. Each line displays different colors

Two methods:
The first datagridview1 Rows[i]. DefaultCellStyle. BAckColor
The second is the AlternatingRowsDefaultCellStyle property, which gets or this is the default cell style applied to odd rows of DataGridView. The RowsDefaultCellStyle property gets or sets the default style of the row cells of the DataGridView

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace _10_DataGridView Each row displays a different color
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);
            The first way
            //for (int i=0; i<this.dataGridView1.Rows.Count;i++)
            //{
            //    if (i % 2 == 0)
            //        this.dataGridView1.Rows[i].DefaultCellStyle.BackColor = Color.Pink;
            //    else
            //        this.dataGridView1.Rows[i].DefaultCellStyle.BackColor = Color.Violet;
            //}

            //Second
            this.dataGridView1.RowsDefaultCellStyle.BackColor = Color.Violet;
            this.dataGridView1.AlternatingRowsDefaultCellStyle.BackColor = Color.SaddleBrown;
        }
    }
}

11. DataGridView paging display

Idea: fill the whole data table into a DataSet, and then part of the reality (DataAdapter Fill overload)
DataGridView
BindingNavigate
bindingSource: associate the data source of DataGridView with BindingNavicat


using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Data.SqlClient;


namespace _11_DataGridView Pagination display
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        private SqlDataAdapter pageDA;
        private DataSet pageDS = new DataSet();
        private int startval = 0; //Starting value
        private int valPerPage = 3;
        private int toalValNumber;  //Total number
        private int currentPage = 1;
        private void Form1_Load(object sender, EventArgs e)
        {
            dataGridView1.AllowUserToAddRows = false;
            string constr = "Server=.;user=sa;pwd=darly;database=csharpzx";
            SqlConnection mycon = new SqlConnection(constr);
            try
            {
                mycon.Open();
                string sql = "select * from mytable";
                pageDA = new SqlDataAdapter(sql, mycon);
                pageDA.Fill(pageDS, "mytable");
                toalValNumber = pageDS.Tables[0].Rows.Count;
                //Calculation of total pages
                int totalPageNumber = (toalValNumber % valPerPage == 0) ? (toalValNumber / valPerPage) : (toalValNumber / valPerPage + 1); //Binocular expression
                toolStripLabel1.Text = "/" + totalPageNumber;
                LoadData();
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
            finally
            {
                mycon.Close();
            }
        }
        private void LoadData()
        {
            currentPage = startval / valPerPage + 1;   //Calculate the initial current page, and the initial value is 0, so the first page of data is opened and displayed for the first time
            toolStripTextBox1.Text = currentPage.ToString();
            pageDS.Clear(); //Empty dataset
            pageDA.Fill(pageDS, startval, valPerPage, "mytable");
            bindingSource1.DataSource = pageDS.Tables[0];          //bindingSource1 binding data source
            bindingNavigator1.BindingSource = bindingSource1;      //BindingNavigator 1 binding data source
            dataGridView1.DataSource = bindingSource1;
            

        }

        private void bindingNavigator1_ItemClicked(object sender, ToolStripItemClickedEventArgs e)
        {
            if (e.ClickedItem.Text == "previous page")
            {
                startval = startval - valPerPage;
                if (startval < 0)
                {
                    MessageBox.Show("It's already the first page");
                    startval = 0;
                    return;
                }

            }
            if (e.ClickedItem.Text == "next page")
            {
                startval = startval + valPerPage;
                if(startval>toalValNumber)
                {
                    MessageBox.Show("It's the last page");
                    startval = startval - valPerPage;
                    return;
                }                
            }
            LoadData();
        }
    }
}

12. DataGridView cell auto fill

In various DataGridView cells, when a specified character is entered, the filling is automatically completed
TextBox has the following two properties through the implementation of TextBox

  • AutoCompleteMode / / there is no auto fill mode by default
    • AutoCompleteMode.Suggest; // The auto fill mode needs to be changed to the suggestion mode. The suggestion mode needs the following properties to provide specific contents
  • AutoCompleteSource
    • AutoCompleteSource.CustomSource / / automatically fill in the data source, set it to the data source defined by the customer, and then define a data source

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace _13_DataGridView Auto fill cells
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            // TODO: this line of code loads the data into the table "csharpzxDataSet.mytable". You can move or delete it as needed.
            this.mytableTableAdapter.Fill(this.csharpzxDataSet.mytable);

        }

        private void dataGridView1_EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e)
        {
            string titleText = dataGridView1.Columns[dataGridView1.CurrentCell.ColumnIndex].HeaderText;
            if(titleText.Equals("department"))
            {
                TextBox autoText = e.Control as TextBox;
                if(autoText !=null)
                {
                    autoText.AutoCompleteMode = AutoCompleteMode.Suggest;
                    autoText.AutoCompleteSource = AutoCompleteSource.CustomSource;
                    AutoCompleteStringCollection dataCollection = new AutoCompleteStringCollection();
                    dataCollection.Add("Development Department");
                    dataCollection.Add("Technology Department");
                    dataCollection.Add("Testing department");
                    autoText.AutoCompleteCustomSource = dataCollection;
                }

            }
        }
    }
}

Summary of this chapter and task implementation

Create employee information table: add name, gender and salary
Draw the line number, and the selected line is displayed in blue
Other lines show different colors
Pagination display

using System;
using System.Data;
using System.Drawing;
using System.Windows.Forms;

namespace _14__Implementation tasks
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        int valToalNum = 500; //Total number of pieces produced
        DataTable dtable;
        int valPerPage = 15;  //Number of entries per page
        int pageNum = 0;   //PageCount 
        int pageCurrent = 1; //Current page serial number
        int valCurrent = 0;   //Current number
        int valstartCurrent = 0;  //Starting number of current page
        int valEndIndex = 0; //Current page termination number

        private void dtGenerate()    //Data generation method
        {
            dtable = new DataTable("ClerkSalary");
            dtable.Columns.Add("full name", Type.GetType("System.String"));
            dtable.Columns.Add("Gender", Type.GetType("System.String"));
            dtable.Columns.Add("wages", Type.GetType("System.Int32"));
            String familyName = "Zhao Qian Sun Li Zhou Wu Zheng Wang Feng Chen Zhu Wei Jiang Shen Cui Hu Liu";
            string lastName = @"The Chinese words of name the surname and first name of a person are given by human beings to distinguish individuals
 Individual specific name symbols distinguish people and individuals through language and text information
 The sign of difference because human beings can communicate normally and orderly with names, so everyone has his own name";
            string gender = "men and women";
            Random rd = new Random();
            for (int i = 0; i < valToalNum; i++)
            {
                //Add line mode 1
                string name = familyName[rd.Next(0, familyName.Length)].ToString() + lastName[rd.Next(0, lastName.Length)].ToString() + lastName[rd.Next(0, lastName.Length)].ToString();
                string Gender = gender[rd.Next(0, gender.Length)].ToString();
                int salary = rd.Next(1800, 10000);
                dtable.Rows.Add(new object[] { name, Gender, salary });

                //Add line mode 2
                //DataRow dr = dtable.NewRow();
                //dr[0] = familyName[rd.Next(0, familyName.Length)].ToString() + lastName[rd.Next(0, lastName.Length)].ToString() + lastName[rd.Next(0, lastName.Length)].ToString();
                //dr[1] = gender[rd.Next(0, gender.Length)].ToString();
                //dr[2] = rd.Next(1800, 1000);
                //dtable.Rows.Add(dr);
            }




        }

        private void loadData()    //Load the data of the current page
        {
            DataTable dtTemp = dtable.Clone();
            if (pageCurrent == pageNum) valEndIndex = valToalNum - 1; //Only one page
            else valEndIndex = pageCurrent * valPerPage - 1;  //More than one page
            valstartCurrent = valCurrent;
            toolStripTextBox1.Text = pageCurrent.ToString();
            toolStripLabel1.Text = "/" + Convert.ToString(pageNum);
            //Read the current data from the original data table
            for (int i = valstartCurrent; i < valEndIndex; i++)
            {
                dtTemp.ImportRow(dtable.Rows[i]);   //Import responses into temporary tables
                valCurrent++;
            }
            //Bind data source
            bindingSource1.DataSource = dtTemp;
            bindingNavigator1.BindingSource = bindingSource1;
            dataGridView1.DataSource = bindingSource1;
            //Parity lines display different colors
            dataGridView1.RowsDefaultCellStyle.BackColor = Color.Pink;
            dataGridView1.AlternatingRowsDefaultCellStyle.BackColor = Color.Violet;

        }

        private void Form1_Load(object sender, EventArgs e)
        {
            try
            {
                dtGenerate();
                //MessageBox.Show("data production completed");
                pageNum = (valToalNum % valPerPage == 0) ? (valToalNum / valPerPage) : (valToalNum / valPerPage + 1);
                loadData();
                dataGridView1.ReadOnly = true;
                dataGridView1.AllowUserToAddRows = false;
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message.ToString());                
            }
        }

        private void dataGridView1_RowPostPaint(object sender, DataGridViewRowPostPaintEventArgs e)
        {
            Rectangle myrec = new Rectangle(e.RowBounds.Location.X, e.RowBounds.Location.Y, dataGridView1.RowHeadersWidth, e.RowBounds.Height);
            //TextRenderer.DrawText(e.Graphics, (e.RowIndex + 1).ToString(), dataGridView1.RowHeadersDefaultCellStyle.Font, myrec, dataGridView1.RowHeadersDefaultCellStyle.ForeColor, TextFormatFlags.VerticalCenter | TextFormatFlags.Right);
            TextRenderer.DrawText(e.Graphics, (e.RowIndex + 1+valstartCurrent).ToString(), dataGridView1.RowHeadersDefaultCellStyle.Font, myrec, dataGridView1.RowHeadersDefaultCellStyle.ForeColor, TextFormatFlags.VerticalCenter | TextFormatFlags.Right);
            if (e.RowIndex >= dataGridView1.Rows.Count - 1) return;  //If the selected line is a new line (content to be added), do not operate and return directly
            Color oldForeColor = new Color();
            Color oldBackColor = new Color();
            // object is the base class of all classes. Var can be all variable types. When the variable type is unknown, it can be declared in var format

            var row = dataGridView1.Rows[e.RowIndex];    //Line of action
            if (row == dataGridView1.CurrentRow)   //Judge whether the operation line is the same as the current line. If it is the same, it represents the first operation, so different styles should be drawn
            {
                if (row.DefaultCellStyle.ForeColor != Color.White) 
                {
                    oldForeColor = row.DefaultCellStyle.ForeColor;  // Store the current foreground color
                    row.DefaultCellStyle.ForeColor = Color.White;   // Set the foreground color to white
                }
                if (row.DefaultCellStyle.BackColor != Color.Blue)
                {
                    oldBackColor = row.DefaultCellStyle.BackColor;
                    row.DefaultCellStyle.BackColor = Color.Blue;
                }
            }
            else
            {
                row.DefaultCellStyle.ForeColor = oldForeColor;
                row.DefaultCellStyle.BackColor = oldBackColor;
            }
        }

        private void bindingNavigator1_ItemClicked(object sender, ToolStripItemClickedEventArgs e)
        {
            if (e.ClickedItem.Text == "previous page")
            {
                pageCurrent--;
                if (pageCurrent <= 0)
                {
                    MessageBox.Show("It's the last page");
                    pageCurrent++;
                    return;
                }
                else
                {
                    valCurrent = valPerPage * (pageCurrent - 1);

                }
                loadData();
            }
            if(e.ClickedItem.Text=="next page")
            {
                pageCurrent++;
                if(pageCurrent>pageNum)
                {
                    pageCurrent--;
                    MessageBox.Show("It's the last page");
                    return;
                }
                else
                {
                    valCurrent = valPerPage * (pageCurrent - 1);
                }
                loadData();

            }
        }
    }
}

Topics: C# Windows UI