DataGrid Combo Box problem

R

Ron L

I have a dataset whose source is a SQL 2k stored procedure that I am trying
to display in a datagrid. This datasource has 4 columns that I am
interested in here, a text column and 3 value columns corresponding to
permissions to certain data classes. I want to put the permission values in
combo boxes in the grid and instead of displaying the numeric values, have
the combo box display a string that corresponds to the numeric value (i.e.
No Access for 0, Read for 1, Create for 3, and Edit for 7). I have written
the code below to try to implement this, but it throws an error on
rendering. The error is:
An unhandled exception of type 'System.InvalidCastException'
occurred in system.windows.forms.dll
Additional information: Specified cast is not valid.
I suspect, but can't be sure, that the cast error has to do with the binding
of the dataset to the pulldown. The column names that I am trying to bind
to are "TSL", "HCT", and "MCT"

Can anyone tell me what I am doing wrong here?
TIA,
Ron L

The code:
' Setup the permissions grid
' Setup the list of Display/Value pairs for the combo
boxes
Dim permsList As DataTable
permsList = New DataTable
permsList.Columns.Add(New DataColumn("Display", GetType(String)))
permsList.Columns.Add(New DataColumn("Id", GetType(Integer)))
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows(0)(0) = "No Access"
permsList.Rows(0)(1) = 0
permsList.Rows(1)(0) = "Read"
permsList.Rows(1)(1) = 1
permsList.Rows(2)(0) = "Create"
permsList.Rows(2)(1) = 3
permsList.Rows(3)(0) = "Edit"
permsList.Rows(3)(1) = 7

' Fill the DataTable from the user data dataset (includes user
permissions)
Dim dt As DataTable = dsUserData.Tables(0)

Dim tableStyle As New DataGridTableStyle
tableStyle.GridColumnStyles.Clear()
tableStyle.MappingName = "Table"
tableStyle.MappingName = dt.TableName.ToString

' Setup the Subsystems column
Dim TextCol As New DataGridTextBoxColumn
TextCol.MappingName = dt.Columns(15).ColumnName
TextCol.HeaderText = dt.Columns(15).ColumnName
tableStyle.GridColumnStyles.Add(TextCol)

' Setup the permissions columns

Dim i As Integer
For i = 2 To 4
'Dim textcol2 As New DataGridTextBoxColumn
'textcol2.MappingName = dt.Columns(i).ColumnName
'textcol2.HeaderText = dt.Columns(i).ColumnName
'tableStyle.GridColumnStyles.Add(textcol2)
Dim ComboTextCol As New DataGridComboBoxColumn
ComboTextCol.MappingName = dt.Columns(i).ColumnName
ComboTextCol.HeaderText = dt.Columns(i).ColumnName
ComboTextCol.Width = 120
ComboTextCol.ColumnComboBox.Items.Clear()
ComboTextCol.ColumnComboBox.DataSource = permsList
ComboTextCol.ColumnComboBox.DisplayMember = "Display"
ComboTextCol.ColumnComboBox.ValueMember =
dt.Columns(i).ColumnName
' for the above line I have also tried setting it equal to "Id"

tableStyle.PreferredRowHeight =
ComboTextCol.ColumnComboBox.Height + 2

tableStyle.GridColumnStyles.Add(ComboTextCol)
Next

grdPermissions.TableStyles.Clear()
grdPermissions.TableStyles.Add(tableStyle)
grdPermissions.DataSource = dt
Dim grdStyle As DataGridTableStyle

'no adding of new rows thru dataview...
Dim cm As CurrencyManager
cm = CType(Me.BindingContext(grdPermissions.DataSource,
grdPermissions.DataMember), CurrencyManager)
CType(cm.List, DataView).AllowNew = False
 
R

Ron L

After some more experimentation (and hair pulling), it seems that the line
that is causing the problem is this one:

ComboTextCol.MappingName = dt.Columns(i).ColumnName

Can anyone tell mw what I am doing wrong here?

TIA
Ron L
 
K

Ken Tucker [MVP]

Hi,

Post the code for the column style

Ken
----------------
I have a dataset whose source is a SQL 2k stored procedure that I am trying
to display in a datagrid. This datasource has 4 columns that I am
interested in here, a text column and 3 value columns corresponding to
permissions to certain data classes. I want to put the permission values in
combo boxes in the grid and instead of displaying the numeric values, have
the combo box display a string that corresponds to the numeric value (i.e.
No Access for 0, Read for 1, Create for 3, and Edit for 7). I have written
the code below to try to implement this, but it throws an error on
rendering. The error is:
An unhandled exception of type 'System.InvalidCastException'
occurred in system.windows.forms.dll
Additional information: Specified cast is not valid.
I suspect, but can't be sure, that the cast error has to do with the binding
of the dataset to the pulldown. The column names that I am trying to bind
to are "TSL", "HCT", and "MCT"

Can anyone tell me what I am doing wrong here?
TIA,
Ron L

The code:
' Setup the permissions grid
' Setup the list of Display/Value pairs for the combo
boxes
Dim permsList As DataTable
permsList = New DataTable
permsList.Columns.Add(New DataColumn("Display", GetType(String)))
permsList.Columns.Add(New DataColumn("Id", GetType(Integer)))
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows(0)(0) = "No Access"
permsList.Rows(0)(1) = 0
permsList.Rows(1)(0) = "Read"
permsList.Rows(1)(1) = 1
permsList.Rows(2)(0) = "Create"
permsList.Rows(2)(1) = 3
permsList.Rows(3)(0) = "Edit"
permsList.Rows(3)(1) = 7

' Fill the DataTable from the user data dataset (includes user
permissions)
Dim dt As DataTable = dsUserData.Tables(0)

Dim tableStyle As New DataGridTableStyle
tableStyle.GridColumnStyles.Clear()
tableStyle.MappingName = "Table"
tableStyle.MappingName = dt.TableName.ToString

' Setup the Subsystems column
Dim TextCol As New DataGridTextBoxColumn
TextCol.MappingName = dt.Columns(15).ColumnName
TextCol.HeaderText = dt.Columns(15).ColumnName
tableStyle.GridColumnStyles.Add(TextCol)

' Setup the permissions columns

Dim i As Integer
For i = 2 To 4
'Dim textcol2 As New DataGridTextBoxColumn
'textcol2.MappingName = dt.Columns(i).ColumnName
'textcol2.HeaderText = dt.Columns(i).ColumnName
'tableStyle.GridColumnStyles.Add(textcol2)
Dim ComboTextCol As New DataGridComboBoxColumn
ComboTextCol.MappingName = dt.Columns(i).ColumnName
ComboTextCol.HeaderText = dt.Columns(i).ColumnName
ComboTextCol.Width = 120
ComboTextCol.ColumnComboBox.Items.Clear()
ComboTextCol.ColumnComboBox.DataSource = permsList
ComboTextCol.ColumnComboBox.DisplayMember = "Display"
ComboTextCol.ColumnComboBox.ValueMember =
dt.Columns(i).ColumnName
' for the above line I have also tried setting it equal to "Id"

tableStyle.PreferredRowHeight =
ComboTextCol.ColumnComboBox.Height + 2

tableStyle.GridColumnStyles.Add(ComboTextCol)
Next

grdPermissions.TableStyles.Clear()
grdPermissions.TableStyles.Add(tableStyle)
grdPermissions.DataSource = dt
Dim grdStyle As DataGridTableStyle

'no adding of new rows thru dataview...
Dim cm As CurrencyManager
cm = CType(Me.BindingContext(grdPermissions.DataSource,
grdPermissions.DataMember), CurrencyManager)
CType(cm.List, DataView).AllowNew = False
 
R

Ron L

Ken
Thanks for the response. I forgot to mention that this is the code from
Ken Shepard's www.syncfusion.com site, the data grid bound combo box column.

Here it is.

Ron L

' DataGridComboBoxColumn.vb - From George Shepard's www.syncfusion.com site.
(The bound
' data grid combo box example.)
Option Strict Off
Option Explicit On

Imports Microsoft.VisualBasic
Imports System
Imports System.ComponentModel
Imports System.Data
Imports System.Data.Common
Imports System.Data.OleDb
Imports System.Drawing
Imports System.Windows.Forms

' Step 1. Derive a custom column style from DataGridTextBoxColumn
' a) add a ComboBox member
' b) track when the combobox has focus in Enter and Leave events
' c) override Edit to allow the ComboBox to replace the TextBox
' d) override Commit to save the changed data
Public Class DataGridComboBoxColumn
Inherits DataGridTextBoxColumn
Public ColumnComboBox As NoKeyUpCombo
Private _source As System.Windows.Forms.CurrencyManager
Private _rowNum As Integer
Private _isEditing As Boolean
Public Shared _RowCount As Integer


Public Sub New()
_source = Nothing
_isEditing = False
_RowCount = -1

ColumnComboBox = New NoKeyUpCombo()
ColumnComboBox.DropDownStyle = ComboBoxStyle.DropDownList

AddHandler ColumnComboBox.Leave, AddressOf LeaveComboBox
AddHandler ColumnComboBox.SelectionChangeCommitted, AddressOf
ComboStartEditing
End Sub 'New

Private Sub HandleScroll(ByVal sender As Object, ByVal e As
EventArgs)
If ColumnComboBox.Visible Then
ColumnComboBox.Hide()
End If
End Sub 'HandleScroll

Private Sub ComboStartEditing(ByVal sender As Object, ByVal e As
EventArgs)
_isEditing = True
MyBase.ColumnStartedEditing(sender)
End Sub 'ComboMadeCurrent


Private Sub LeaveComboBox(ByVal sender As Object, ByVal e As
EventArgs)
If _isEditing Then
SetColumnValueAtRow(_source, _rowNum, ColumnComboBox.Text)
_isEditing = False
Invalidate()

End If
ColumnComboBox.Hide()
AddHandler Me.DataGridTableStyle.DataGrid.Scroll, New
EventHandler(AddressOf HandleScroll)
End Sub 'LeaveComboBox


Protected Overloads Overrides Sub Edit(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer, ByVal bounds
As System.Drawing.Rectangle, ByVal [readOnly] As Boolean, ByVal instantText
As String, ByVal cellIsVisible As Boolean)

MyBase.Edit([source], rowNum, bounds, [readOnly], instantText,
cellIsVisible)

_rowNum = rowNum
_source = [source]

ColumnComboBox.Parent = Me.TextBox.Parent
ColumnComboBox.Location = Me.TextBox.Location
ColumnComboBox.Size = New Size(Me.TextBox.Size.Width,
ColumnComboBox.Size.Height)
ColumnComboBox.SelectedIndex =
ColumnComboBox.FindStringExact(Me.TextBox.Text)
ColumnComboBox.Text = Me.TextBox.Text
Me.TextBox.Visible = False
ColumnComboBox.Visible = True
AddHandler Me.DataGridTableStyle.DataGrid.Scroll, AddressOf
HandleScroll

ColumnComboBox.BringToFront()
ColumnComboBox.Focus()
End Sub 'Edit


Protected Overrides Function Commit(ByVal dataSource As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer) As Boolean

If _isEditing Then
_isEditing = False
SetColumnValueAtRow(dataSource, rowNum, ColumnComboBox.Text)
End If
Return True
End Function 'Commit


Protected Overrides Sub ConcedeFocus()
Console.WriteLine("ConcedeFocus")
MyBase.ConcedeFocus()
End Sub 'ConcedeFocus

Protected Overrides Function GetColumnValueAtRow(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer) As Object

Dim s As Object = MyBase.GetColumnValueAtRow([source], rowNum)
Dim dv As DataView = CType(Me.ColumnComboBox.DataSource,
DataView)
Dim rowCount As Integer = dv.Count
Dim i As Integer = 0
Dim s1 As Object

'if things are slow, you could order your dataview
'& use binary search instead of this linear one
While i < rowCount
s1 = dv(i)(Me.ColumnComboBox.ValueMember)
If (Not s1 Is DBNull.Value) AndAlso _
(Not s Is DBNull.Value) AndAlso _
s = s1 Then
Exit While
End If
i = i + 1
End While

If i < rowCount Then
Return dv(i)(Me.ColumnComboBox.DisplayMember)
End If
Return DBNull.Value
End Function 'GetColumnValueAtRow


Protected Overrides Sub SetColumnValueAtRow(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer, ByVal value
As Object)
Dim s As Object = value

Dim dv As DataView = CType(Me.ColumnComboBox.DataSource,
DataView)
Dim rowCount As Integer = dv.Count
Dim i As Integer = 0
Dim s1 As Object

'if things are slow, you could order your dataview
'& use binary search instead of this linear one
While i < rowCount
s1 = dv(i)(Me.ColumnComboBox.DisplayMember)
If (Not s1 Is DBNull.Value) AndAlso _
s = s1 Then
Exit While
End If
i = i + 1
End While
If i < rowCount Then
s = dv(i)(Me.ColumnComboBox.ValueMember)
Else
s = DBNull.Value
End If
MyBase.SetColumnValueAtRow([source], rowNum, s)
End Sub 'SetColumnValueAtRow


End Class 'DataGridComboBoxColumn
 
R

Ron L

One of my co-workers found the problem. I needed the .DefaultView on the
table in my Datasource mapping:

ComboTextCol.ColumnComboBox.DataSource = permsList.Copy.DefaultView

Ron L
 
K

Ken Tucker [MVP]

Hi,

I dont see any line of code with an error. What i would suggest
is to place a break point in the start of each procedure in the columnstyle.
Step through the code line by line until you find the error.

Ken
----------------
Ken
Thanks for the response. I forgot to mention that this is the code from
Ken Shepard's www.syncfusion.com site, the data grid bound combo box column.

Here it is.

Ron L

' DataGridComboBoxColumn.vb - From George Shepard's www.syncfusion.com site.
(The bound
' data grid combo box example.)
Option Strict Off
Option Explicit On

Imports Microsoft.VisualBasic
Imports System
Imports System.ComponentModel
Imports System.Data
Imports System.Data.Common
Imports System.Data.OleDb
Imports System.Drawing
Imports System.Windows.Forms

' Step 1. Derive a custom column style from DataGridTextBoxColumn
' a) add a ComboBox member
' b) track when the combobox has focus in Enter and Leave events
' c) override Edit to allow the ComboBox to replace the TextBox
' d) override Commit to save the changed data
Public Class DataGridComboBoxColumn
Inherits DataGridTextBoxColumn
Public ColumnComboBox As NoKeyUpCombo
Private _source As System.Windows.Forms.CurrencyManager
Private _rowNum As Integer
Private _isEditing As Boolean
Public Shared _RowCount As Integer


Public Sub New()
_source = Nothing
_isEditing = False
_RowCount = -1

ColumnComboBox = New NoKeyUpCombo()
ColumnComboBox.DropDownStyle = ComboBoxStyle.DropDownList

AddHandler ColumnComboBox.Leave, AddressOf LeaveComboBox
AddHandler ColumnComboBox.SelectionChangeCommitted, AddressOf
ComboStartEditing
End Sub 'New

Private Sub HandleScroll(ByVal sender As Object, ByVal e As
EventArgs)
If ColumnComboBox.Visible Then
ColumnComboBox.Hide()
End If
End Sub 'HandleScroll

Private Sub ComboStartEditing(ByVal sender As Object, ByVal e As
EventArgs)
_isEditing = True
MyBase.ColumnStartedEditing(sender)
End Sub 'ComboMadeCurrent


Private Sub LeaveComboBox(ByVal sender As Object, ByVal e As
EventArgs)
If _isEditing Then
SetColumnValueAtRow(_source, _rowNum, ColumnComboBox.Text)
_isEditing = False
Invalidate()

End If
ColumnComboBox.Hide()
AddHandler Me.DataGridTableStyle.DataGrid.Scroll, New
EventHandler(AddressOf HandleScroll)
End Sub 'LeaveComboBox


Protected Overloads Overrides Sub Edit(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer, ByVal bounds
As System.Drawing.Rectangle, ByVal [readOnly] As Boolean, ByVal instantText
As String, ByVal cellIsVisible As Boolean)

MyBase.Edit([source], rowNum, bounds, [readOnly], instantText,
cellIsVisible)

_rowNum = rowNum
_source = [source]

ColumnComboBox.Parent = Me.TextBox.Parent
ColumnComboBox.Location = Me.TextBox.Location
ColumnComboBox.Size = New Size(Me.TextBox.Size.Width,
ColumnComboBox.Size.Height)
ColumnComboBox.SelectedIndex =
ColumnComboBox.FindStringExact(Me.TextBox.Text)
ColumnComboBox.Text = Me.TextBox.Text
Me.TextBox.Visible = False
ColumnComboBox.Visible = True
AddHandler Me.DataGridTableStyle.DataGrid.Scroll, AddressOf
HandleScroll

ColumnComboBox.BringToFront()
ColumnComboBox.Focus()
End Sub 'Edit


Protected Overrides Function Commit(ByVal dataSource As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer) As Boolean

If _isEditing Then
_isEditing = False
SetColumnValueAtRow(dataSource, rowNum, ColumnComboBox.Text)
End If
Return True
End Function 'Commit


Protected Overrides Sub ConcedeFocus()
Console.WriteLine("ConcedeFocus")
MyBase.ConcedeFocus()
End Sub 'ConcedeFocus

Protected Overrides Function GetColumnValueAtRow(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer) As Object

Dim s As Object = MyBase.GetColumnValueAtRow([source], rowNum)
Dim dv As DataView = CType(Me.ColumnComboBox.DataSource,
DataView)
Dim rowCount As Integer = dv.Count
Dim i As Integer = 0
Dim s1 As Object

'if things are slow, you could order your dataview
'& use binary search instead of this linear one
While i < rowCount
s1 = dv(i)(Me.ColumnComboBox.ValueMember)
If (Not s1 Is DBNull.Value) AndAlso _
(Not s Is DBNull.Value) AndAlso _
s = s1 Then
Exit While
End If
i = i + 1
End While

If i < rowCount Then
Return dv(i)(Me.ColumnComboBox.DisplayMember)
End If
Return DBNull.Value
End Function 'GetColumnValueAtRow


Protected Overrides Sub SetColumnValueAtRow(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer, ByVal value
As Object)
Dim s As Object = value

Dim dv As DataView = CType(Me.ColumnComboBox.DataSource,
DataView)
Dim rowCount As Integer = dv.Count
Dim i As Integer = 0
Dim s1 As Object

'if things are slow, you could order your dataview
'& use binary search instead of this linear one
While i < rowCount
s1 = dv(i)(Me.ColumnComboBox.DisplayMember)
If (Not s1 Is DBNull.Value) AndAlso _
s = s1 Then
Exit While
End If
i = i + 1
End While
If i < rowCount Then
s = dv(i)(Me.ColumnComboBox.ValueMember)
Else
s = DBNull.Value
End If
MyBase.SetColumnValueAtRow([source], rowNum, s)
End Sub 'SetColumnValueAtRow


End Class 'DataGridComboBoxColumn
 
R

Ron L

Ken
As you can see from my later post, we found the problem. I had tried
the single stepping that you suggested, but the error didn't show up in any
line of code I had written. My subroutines finished without errors, but the
error was thrown when the form tried to render. Apparently the lack of the
..DefaultView call caused some problem when the rendering occurred.

Thanks for the help.
Ron L

Ken Tucker said:
Hi,

I dont see any line of code with an error. What i would
suggest
is to place a break point in the start of each procedure in the
columnstyle.
Step through the code line by line until you find the error.

Ken
----------------
Ken
Thanks for the response. I forgot to mention that this is the code
from
Ken Shepard's www.syncfusion.com site, the data grid bound combo box
column.

Here it is.

Ron L

' DataGridComboBoxColumn.vb - From George Shepard's www.syncfusion.com
site.
(The bound
' data grid combo box example.)
Option Strict Off
Option Explicit On

Imports Microsoft.VisualBasic
Imports System
Imports System.ComponentModel
Imports System.Data
Imports System.Data.Common
Imports System.Data.OleDb
Imports System.Drawing
Imports System.Windows.Forms

' Step 1. Derive a custom column style from DataGridTextBoxColumn
' a) add a ComboBox member
' b) track when the combobox has focus in Enter and Leave events
' c) override Edit to allow the ComboBox to replace the TextBox
' d) override Commit to save the changed data
Public Class DataGridComboBoxColumn
Inherits DataGridTextBoxColumn
Public ColumnComboBox As NoKeyUpCombo
Private _source As System.Windows.Forms.CurrencyManager
Private _rowNum As Integer
Private _isEditing As Boolean
Public Shared _RowCount As Integer


Public Sub New()
_source = Nothing
_isEditing = False
_RowCount = -1

ColumnComboBox = New NoKeyUpCombo()
ColumnComboBox.DropDownStyle = ComboBoxStyle.DropDownList

AddHandler ColumnComboBox.Leave, AddressOf LeaveComboBox
AddHandler ColumnComboBox.SelectionChangeCommitted, AddressOf
ComboStartEditing
End Sub 'New

Private Sub HandleScroll(ByVal sender As Object, ByVal e As
EventArgs)
If ColumnComboBox.Visible Then
ColumnComboBox.Hide()
End If
End Sub 'HandleScroll

Private Sub ComboStartEditing(ByVal sender As Object, ByVal e As
EventArgs)
_isEditing = True
MyBase.ColumnStartedEditing(sender)
End Sub 'ComboMadeCurrent


Private Sub LeaveComboBox(ByVal sender As Object, ByVal e As
EventArgs)
If _isEditing Then
SetColumnValueAtRow(_source, _rowNum, ColumnComboBox.Text)
_isEditing = False
Invalidate()

End If
ColumnComboBox.Hide()
AddHandler Me.DataGridTableStyle.DataGrid.Scroll, New
EventHandler(AddressOf HandleScroll)
End Sub 'LeaveComboBox


Protected Overloads Overrides Sub Edit(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer, ByVal
bounds
As System.Drawing.Rectangle, ByVal [readOnly] As Boolean, ByVal
instantText
As String, ByVal cellIsVisible As Boolean)

MyBase.Edit([source], rowNum, bounds, [readOnly], instantText,
cellIsVisible)

_rowNum = rowNum
_source = [source]

ColumnComboBox.Parent = Me.TextBox.Parent
ColumnComboBox.Location = Me.TextBox.Location
ColumnComboBox.Size = New Size(Me.TextBox.Size.Width,
ColumnComboBox.Size.Height)
ColumnComboBox.SelectedIndex =
ColumnComboBox.FindStringExact(Me.TextBox.Text)
ColumnComboBox.Text = Me.TextBox.Text
Me.TextBox.Visible = False
ColumnComboBox.Visible = True
AddHandler Me.DataGridTableStyle.DataGrid.Scroll, AddressOf
HandleScroll

ColumnComboBox.BringToFront()
ColumnComboBox.Focus()
End Sub 'Edit


Protected Overrides Function Commit(ByVal dataSource As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer) As Boolean

If _isEditing Then
_isEditing = False
SetColumnValueAtRow(dataSource, rowNum,
ColumnComboBox.Text)
End If
Return True
End Function 'Commit


Protected Overrides Sub ConcedeFocus()
Console.WriteLine("ConcedeFocus")
MyBase.ConcedeFocus()
End Sub 'ConcedeFocus

Protected Overrides Function GetColumnValueAtRow(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer) As Object

Dim s As Object = MyBase.GetColumnValueAtRow([source], rowNum)
Dim dv As DataView = CType(Me.ColumnComboBox.DataSource,
DataView)
Dim rowCount As Integer = dv.Count
Dim i As Integer = 0
Dim s1 As Object

'if things are slow, you could order your dataview
'& use binary search instead of this linear one
While i < rowCount
s1 = dv(i)(Me.ColumnComboBox.ValueMember)
If (Not s1 Is DBNull.Value) AndAlso _
(Not s Is DBNull.Value) AndAlso _
s = s1 Then
Exit While
End If
i = i + 1
End While

If i < rowCount Then
Return dv(i)(Me.ColumnComboBox.DisplayMember)
End If
Return DBNull.Value
End Function 'GetColumnValueAtRow


Protected Overrides Sub SetColumnValueAtRow(ByVal [source] As
System.Windows.Forms.CurrencyManager, ByVal rowNum As Integer, ByVal value
As Object)
Dim s As Object = value

Dim dv As DataView = CType(Me.ColumnComboBox.DataSource,
DataView)
Dim rowCount As Integer = dv.Count
Dim i As Integer = 0
Dim s1 As Object

'if things are slow, you could order your dataview
'& use binary search instead of this linear one
While i < rowCount
s1 = dv(i)(Me.ColumnComboBox.DisplayMember)
If (Not s1 Is DBNull.Value) AndAlso _
s = s1 Then
Exit While
End If
i = i + 1
End While
If i < rowCount Then
s = dv(i)(Me.ColumnComboBox.ValueMember)
Else
s = DBNull.Value
End If
MyBase.SetColumnValueAtRow([source], rowNum, s)
End Sub 'SetColumnValueAtRow


End Class 'DataGridComboBoxColumn

Ken Tucker said:
Hi,

Post the code for the column style

Ken
----------------
I have a dataset whose source is a SQL 2k stored procedure that I am
trying
to display in a datagrid. This datasource has 4 columns that I am
interested in here, a text column and 3 value columns corresponding to
permissions to certain data classes. I want to put the permission values
in
combo boxes in the grid and instead of displaying the numeric values,
have
the combo box display a string that corresponds to the numeric value
(i.e.
No Access for 0, Read for 1, Create for 3, and Edit for 7). I have
written
the code below to try to implement this, but it throws an error on
rendering. The error is:
An unhandled exception of type 'System.InvalidCastException'
occurred in system.windows.forms.dll
Additional information: Specified cast is not valid.
I suspect, but can't be sure, that the cast error has to do with the
binding
of the dataset to the pulldown. The column names that I am trying to
bind
to are "TSL", "HCT", and "MCT"

Can anyone tell me what I am doing wrong here?
TIA,
Ron L

The code:
' Setup the permissions grid
' Setup the list of Display/Value pairs for the combo
boxes
Dim permsList As DataTable
permsList = New DataTable
permsList.Columns.Add(New DataColumn("Display", GetType(String)))
permsList.Columns.Add(New DataColumn("Id", GetType(Integer)))
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows.Add(permsList.NewRow())
permsList.Rows(0)(0) = "No Access"
permsList.Rows(0)(1) = 0
permsList.Rows(1)(0) = "Read"
permsList.Rows(1)(1) = 1
permsList.Rows(2)(0) = "Create"
permsList.Rows(2)(1) = 3
permsList.Rows(3)(0) = "Edit"
permsList.Rows(3)(1) = 7

' Fill the DataTable from the user data dataset (includes user
permissions)
Dim dt As DataTable = dsUserData.Tables(0)

Dim tableStyle As New DataGridTableStyle
tableStyle.GridColumnStyles.Clear()
tableStyle.MappingName = "Table"
tableStyle.MappingName = dt.TableName.ToString

' Setup the Subsystems column
Dim TextCol As New DataGridTextBoxColumn
TextCol.MappingName = dt.Columns(15).ColumnName
TextCol.HeaderText = dt.Columns(15).ColumnName
tableStyle.GridColumnStyles.Add(TextCol)

' Setup the permissions columns

Dim i As Integer
For i = 2 To 4
'Dim textcol2 As New DataGridTextBoxColumn
'textcol2.MappingName = dt.Columns(i).ColumnName
'textcol2.HeaderText = dt.Columns(i).ColumnName
'tableStyle.GridColumnStyles.Add(textcol2)
Dim ComboTextCol As New DataGridComboBoxColumn
ComboTextCol.MappingName = dt.Columns(i).ColumnName
ComboTextCol.HeaderText = dt.Columns(i).ColumnName
ComboTextCol.Width = 120
ComboTextCol.ColumnComboBox.Items.Clear()
ComboTextCol.ColumnComboBox.DataSource = permsList
ComboTextCol.ColumnComboBox.DisplayMember = "Display"
ComboTextCol.ColumnComboBox.ValueMember =
dt.Columns(i).ColumnName
' for the above line I have also tried setting it equal to "Id"

tableStyle.PreferredRowHeight =
ComboTextCol.ColumnComboBox.Height + 2

tableStyle.GridColumnStyles.Add(ComboTextCol)
Next

grdPermissions.TableStyles.Clear()
grdPermissions.TableStyles.Add(tableStyle)
grdPermissions.DataSource = dt
Dim grdStyle As DataGridTableStyle

'no adding of new rows thru dataview...
Dim cm As CurrencyManager
cm = CType(Me.BindingContext(grdPermissions.DataSource,
grdPermissions.DataMember), CurrencyManager)
CType(cm.List, DataView).AllowNew = False
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top