vb.net DataGridView prevent user clicking on column

1

I have a DataGridView (DGV) that I am adding items to from a SQLite DB MANUALLY
My setting for the Selection Mode have been CellSelect and FullRowSelect may have tried others

The Errors and Issues are varied depending on where the user clicks on the DGV
The code as it is now the Errors only occur when an empty Column under Header PID is selected
And when the Column Header PID is selected See Posted Image
I have included the ERRORS as comments in the code

One of the issues I would like to FIX is to disable all sorting on all Columns
The Data added to the DGV is a primary key which is a Integer PID
And some text which is a NVARCHAR(2048) this text is from a RichTextBox

The two biggest issue to fix is preventing the ERRORS YES those are the Questions

    Private Sub PopulateDGV()
    For Each header As DataGridViewHeaderCell In dgvOne.Rows
        'header.SortMode = DataGridViewColumnHeaderCell.NotSortable
    Next
    'The code Above NOT Working

    'ERRORS
    'System.InvalidOperationException 'Column's SortMode cannot be set to Automatic
    'While the DataGridView control's SelectionMode is set to ColumnHeaderSelect.'
    'Your app has entered a break state, but there is no code to show because all 
    'threads were executing external code (typically system Or framework code).

    'dgvOne = DataGridViewColumnSortMode.NotSortable
    Dim str2 As String
    Dim s1 As Integer
    Dim dbName As String = "Word.db"
    Dim conn As New SQLiteConnection("Data Source =" & dbName & ";Version=3;")
    Dim valuesList As ArrayList = New ArrayList()

    'Read from the database
    Dim cmd As SQLiteCommand = New SQLiteCommand("Select * FROM ParentTable", conn)
    conn.Open()
    Dim rdr As SQLite.SQLiteDataReader = cmd.ExecuteReader

    'Set Design of the DataGridView
    dgvOne.DefaultCellStyle.Font = New Font("Tahoma", 10)

    dgvOne.ColumnCount = 2
    dgvOne.Columns(0).Width = 60
    dgvOne.Columns(1).Width = 420
    'Set Col Header Size Mode = Enabled
    'Set Col Header Default Cell Styles DO in Properties
    dgvOne.ColumnHeadersHeight = 34

    'DGV Header Names
    dgvOne.Columns(0).Name = "PID"
    dgvOne.Columns(1).Name = "Entry Data"

    'Read from DB Table add to DGV row
    While rdr.Read()
        valuesList.Add(rdr(1)).ToString()
        lbOne.Items.Add(rdr(1)).ToString()
        s1 = rdr(0).ToString
        str2 = rdr(1)
        dgvOne.Rows.Add(s1, str2)
    End While

    'Add Blank rows to DGV
    For iA = 1 To 4
        dgvOne.Rows.Add(" ")
    Next

    rdr.Close()
    conn.Close()

End Sub

Private Sub dgvTwo_CellMouseClick(sender As System.Object, e As System.Windows.Forms.DataGridViewCellMouseEventArgs) Handles dgvOne.CellMouseClick

    If (e.RowIndex = -1) Then
        MessageBox.Show("No Clicking Here")
        Return
    End If

    If dgvOne.CurrentCell.Value Is Nothing Then
        tbMessage.Text = "NO Data Here"
        Return
    ElseIf e.RowIndex >= 0 Then

        tbMessage.Text = e.RowIndex
        Dim str2 As String
        Dim s2 As String
        Dim row As DataGridViewRow = dgvOne.Rows(e.RowIndex)
        s2 = row.Cells(0).Value.ToString
        str2 = row.Cells(1).Value.ToString
        strB = str2
        rtbEnter.Text = strB
        'ERRORS
        'System.NullReferenceException
        'HResult = 0x80004003
        'Message = Object reference Not Set To an instance Of an Object.
        'Source = TestSQL
        'StackTrace:
        'at TestSQL.frmThree.dgvTwo_CellMouseClick(Object sender, DataGridViewCellMouseEventArgs e) in C:\Users\Dwight\source\repos\TestSQL\TestSQL\frmThree.vb:line 117

    End If
End Sub

DGV

vb.net
datagridview
asked on Stack Overflow Jul 14, 2020 by Vector

3 Answers

3

To prevent sorting on columns, which appears to be your main question, do the following:

dgvOne.Columns(0).SortMode = DataGridViewColumnSortMode.NotSortable
dgvOne.Columns(1).SortMode = DataGridViewColumnSortMode.NotSortable

You also need to guard against null values in cells. So in the "CellMouseClick" event, add something like this:

If row.Cells(1).Value IsNot Nothing Then
   str2 = row.Cells(1).Value.ToString
End If
answered on Stack Overflow Jul 14, 2020 by Brian M Stafford • edited Jul 14, 2020 by Brian M Stafford
1

@Brian M Stafford Thanks for getting us headed in the correct direction Vector this is easy to figure out if someone would have shared a little information GREAT Questions's guess your were saving bytes Because you only have three (3) Columns here are their names and positions in the DGV
Col -1 Col 0 Col 1 and YES they go Left to Right
Just So No One Gets Confused Rows go Top to Bottom
Row 0
Row 1
So all you really needed was one more test that delt with ColumnIndex
This code only permits clicking on Column 1 provided it has text in that CELL
Just manipulate the tests and you can provide the user additional selections

    Public Sub dgvTwo_CellMouseClick(sender As System.Object, e As System.Windows.Forms.DataGridViewCellMouseEventArgs) Handles dgvOne.CellMouseClick

    If e.RowIndex = -1 Or e.ColumnIndex = -1 Then
        'tbMessage.Text = "Col " & e.ColumnIndex & " ROW " & e.RowIndex
        tbMessage.Text = "No Clicking Here"
        Return
    End If

    If dgvOne.CurrentCell.Value Is Nothing Then
        tbMessage.Text = "NO Data Here"
        Return
    End If
    Dim s3 As Integer
    s3 = e.ColumnIndex
    If s3 = 0 Then
        'tbMessage.Text = "S3 " & e.ColumnIndex
        tbMessage.Text = "No Clicking Here"
        Return
    End If

    Dim row As DataGridViewRow = dgvOne.Rows(e.RowIndex)
    Dim col As DataGridViewColumn = dgvOne.Columns(e.ColumnIndex)
    If e.RowIndex >= 0 And e.ColumnIndex <> -1 Then

        tbMessage.Text = "Data Sent to RTB"
        Dim str2 As String
        str2 = row.Cells(1).Value.ToString
        rtbEnter.Text = str2
    End If

End Sub
answered on Stack Overflow Jul 15, 2020 by James_Duh
1

After reading all the nice answers and looking for a way to accomplish my multitude of issues and a lot of trial and error here is one way to deal with preventing the user from clicking on various location on the DataGridView

    Public Sub dgvTwo_CellMouseClick(sender As System.Object, e As System.Windows.Forms.DataGridViewCellMouseEventArgs) Handles dgvOne.CellMouseClick

    If e.RowIndex = -1 Or e.ColumnIndex = -1 Then
        'tbMessage.Text = "Col " & e.ColumnIndex & " ROW " & e.RowIndex
        tbMessage.Text = "No Clicking Here"
        rtbEnter.Clear()
        Return
    End If

    Dim str1 As String
    Dim str2 As String
    Dim s1 As Integer
    Dim row As DataGridViewRow = dgvOne.Rows(e.RowIndex)
    str1 = dgvOne.CurrentRow.Cells(0).Value.ToString
    If str1 IsNot " " Then
        If str1 Is " " Then
            Return
        End If
        tbMessage.Text = "Text Sent to RTB"
        s1 = row.Cells(0).Value
        'Dim strInt As String
        gv_passInt = s1.ToString
        str2 = row.Cells(1).Value.ToString
        rtbEnter.Text = str2
        gv_passStr = str2
        Return
    End If
    rtbEnter.Clear()
    tbMessage.Text = "No Data Here"

End Sub
answered on Stack Overflow Jul 17, 2020 by Vector

User contributions licensed under CC BY-SA 3.0