Change DataGridView cell background color question


#1

Hi all,
I am using a DataGridView to handle my project’s data,I got stuck with changing cell’s background color,my goal is change color like these steps:

1.Press button “btn_change_color_01”,change color from cell 1 to 3
2.Press button “btn_change_color_02”,change color from cell 3 to 5
3.Press button “btn_change_color_03”,change color from cell 5 to 8

But when I clear the color and set color to new cells,the result was weird like below,does anyone knows how to fix it?

The codes:

(	
	global DataGridViewTest
	try (destroydialog DataGridViewTest) catch()
	change_color=(dotnetclass "system.drawing.color").fromARGB 12 128 232
	rollout DataGridViewTest "DataGridView"
	(  		 
		dotnetcontrol dgv "DataGridView"  width:295 height:300 pos:[0,0] align:#center
		 
		button btn_change_color_01 "Change Color 01" pos:[105,325] width:110 height:25 
		button btn_change_color_02 "Change Color 02" pos:[105,365] width:110 height:25 
		button btn_change_color_03 "Change Color 03" pos:[105,405] width:110 height:25 
		 
		on DataGridViewTest open do
		(
			 
  			dgv.Dock=dgv.Dock.Fill
  			dgv.RowHeadersVisible=false 			
  			dgv.columns.add (dotnetobject "DataGridViewCheckBoxColumn")
  			dgv.columns.add (dotnetobject "DataGridViewTextBoxColumn")  			
  			
  			for i=0 to dgv.Columns.count-1 do dgv.Columns.Item[i].width=145
  			numCells=dgv.Columns.count-1
			
  			oddColor=(dotnetclass "system.drawing.color").fromARGB 243 243 243
			evenColor= (dotnetclass "system.drawing.color").fromARGB 255 255 255  			
			dgv.defaultCellStyle.backColor=evenColor
			dgv.AlternatingRowsDefaultCellStyle.backColor=oddColor		
			
			dgv.SelectionMode=(dotNetClass "System.Windows.Forms.DataGridViewSelectionMode").FullRowSelect
			
  			for i=1 to 10 do
  			(
				row=dgv.rows.item[dgv.rows.add()]
  				rowCells=row.cells		
			)
			dgv.ClearSelection()
		)
		Fn Clear_color=
		(
			for j=0 to 1 do			
			(
				for i=0 to (dgv.rows.count-1) do
				(
					dgv.rows.item[i].cells.item[j].Style.BackColor=undefined
				)
			)
		)
		on btn_change_color_01 pressed do
		(
			Clear_color()
			for j=0 to 1 do
			(
				for i=1 to 3 do
				(
					dgv.rows.item[i].cells.item[j].Style.BackColor=change_color
				)
			)	
		)
		on btn_change_color_02 pressed do
		(		
			Clear_color()	
			for j=0 to 1 do
			(
				for i=3 to 5 do
				(
					dgv.rows.item[i].cells.item[j].Style.BackColor=change_color
				)
			)	
		)
		on btn_change_color_03 pressed do
		(
			Clear_color()
			for j=0 to 1 do
			(
				for i=5 to 8 do
				(
					dgv.rows.item[i].cells.item[j].Style.BackColor=change_color
				)
			)	
		)
  	 )
  	 createdialog DataGridViewTest 300 450
)

#2

use full row background color:

         row.DefaultCellStyle.BackColor

#3

I tried ,it seems still does not work

(	
	global DataGridViewTest
	try (destroydialog DataGridViewTest) catch()
	change_color=(dotnetclass "system.drawing.color").fromARGB 12 128 232
	defalut_color=(dotnetclass "system.drawing.color").fromARGB 255 255 255
	rollout DataGridViewTest "DataGridView"
	(  		 
		dotnetcontrol dgv "DataGridView"  width:295 height:300 pos:[0,0] align:#center
		 
		button btn_change_color_01 "Change Color 01" pos:[105,325] width:110 height:25 
		button btn_change_color_02 "Change Color 02" pos:[105,365] width:110 height:25 
		button btn_change_color_03 "Change Color 03" pos:[105,405] width:110 height:25 
		 
		on DataGridViewTest open do
		(
			 
  			dgv.Dock=dgv.Dock.Fill
  			dgv.RowHeadersVisible=false 			
  			dgv.columns.add (dotnetobject "DataGridViewCheckBoxColumn")
  			dgv.columns.add (dotnetobject "DataGridViewTextBoxColumn")  			
  			
  			for i=0 to dgv.Columns.count-1 do dgv.Columns.Item[i].width=145
  			numCells=dgv.Columns.count-1
			
  			oddColor=(dotnetclass "system.drawing.color").fromARGB 243 243 243
			evenColor= (dotnetclass "system.drawing.color").fromARGB 255 255 255  			
			dgv.defaultCellStyle.backColor=evenColor
			dgv.AlternatingRowsDefaultCellStyle.backColor=oddColor		
			
			dgv.SelectionMode=(dotNetClass "System.Windows.Forms.DataGridViewSelectionMode").FullRowSelect
			
  			for i=1 to 10 do
  			(
				row=dgv.rows.item[dgv.rows.add()]
  				rowCells=row.cells		
			)
			dgv.ClearSelection()
		)
		Fn Clear_color=
		(			
			for i=0 to (dgv.rows.count-1) do
			(
				dgv.rows.item[i].DefaultCellStyle.BackColor=defalut_color
			)
		)
		on btn_change_color_01 pressed do
		(
			Clear_color()
			for i=1 to 3 do
			(
				dgv.rows.item[i].DefaultCellStyle.BackColor=change_color
			)
		)
		on btn_change_color_02 pressed do
		(		
			Clear_color()
			for i=3 to 5 do
			(
				dgv.rows.item[i].DefaultCellStyle.BackColor=change_color
			)	
		)
		on btn_change_color_03 pressed do
		(
			Clear_color()
			for i=5 to 8 do
			(
				dgv.rows.item[i].DefaultCellStyle.BackColor=change_color
			)	
		)
  	 )
  	 createdialog DataGridViewTest 300 450
)

#4
try (destroydialog DataGridViewRol) catch()
rollout DataGridViewRol "DataGridView" width:206
(  	
	local dot_color = (dotnetclass "system.drawing.color")
	fn make_dot_color rgb = 
	(
		dot_color.fromARGB rgb.r rgb.g rgb.b
	)
	
	dotnetcontrol dgv "DataGridView" width:206 height:260 pos:[1,0] align:#center
	button change_color_bt "Change Color" width:188 align:#left offset:[-4,0] 
	
	on change_color_bt pressed do
	(
		for k=0 to dgv.rows.count-1 do dgv.rows.item[k].DefaultCellStyle.BackColor = make_dot_color (random red green)		
	)
	
	on DataGridViewRol open do
	(
		 
		dgv.Dock = dgv.Dock.Fill
		dgv.RowHeadersVisible = false 			
		dgv.columns.add (dotnetobject "DataGridViewCheckBoxColumn")
				
		dgv.SelectionMode = dgv.SelectionMode.FullRowSelect
		
		dgv.RowCount = 3
		dgv.ColumnCount = 2

		dgv.InvalidateColumn 1
		
		change_color_bt.pressed()
	)
 )
 createdialog DataGridViewRol

#5

Thanks for help,Denis,base on your code,if I want to switch the color with 2 buttons,how could I make it to work?The codes below,when you press button 1 ,it works,but when you press button 2, the color does not changes.

try (destroydialog DataGridViewRol) catch()
rollout DataGridViewRol "DataGridView" width:206
(  	
	local dot_color = (dotnetclass "System.Drawing.Color")
	fn make_dot_color rgb = 
	(
		dot_color.FromARGB rgb.r rgb.g rgb.b
	)
	
	dotnetcontrol dgv "DataGridView" width:206 height:260 pos:[1,0] align:#center
	button change_color_bt1 "Change Color1" width:188 align:#left offset:[-4,0] 
	button change_color_bt2 "Change Color2" width:188 align:#left offset:[-4,0]
	
	on change_color_bt1 pressed do
	(
		dgv.rows.item[0].DefaultCellStyle.BackColor =(dotnetclass "System.Drawing.Color").FromARGB 188 188 188
		dgv.rows.item[1].DefaultCellStyle.BackColor =(dotnetclass "System.Drawing.Color").FromARGB 45 155 155
	)
	on change_color_bt2 pressed do
	(
		dgv.rows.item[0].DefaultCellStyle.BackColor =(dotnetclass "System.Drawing.Color").FromARGB 45 155 155
		dgv.rows.item[1].DefaultCellStyle.BackColor =(dotnetclass "System.Drawing.Color").FromARGB 188 188 188
	)	
	on DataGridViewRol open do
	(
		 
		dgv.Dock = dgv.Dock.Fill
		dgv.RowHeadersVisible = false 			
		dgv.columns.add (dotnetobject "DataGridViewCheckBoxColumn")
				
		dgv.SelectionMode = dgv.SelectionMode.FullRowSelect
		
		dgv.RowCount = 3
		dgv.ColumnCount = 2

		dgv.InvalidateColumn 1
		dgv.clearselection()
		--change_color_bt.pressed()
	)
 )
 createdialog DataGridViewRol

#6

hmm… it’s not so easy as i thought.
let me think more


#7

:sweat_smile:
Indeed…


#8

i have at least three different solutions… which one to use depends on what you really need.
tell your scenario with more details . also, how big is your grid view expected?


#9

I want to use grid to handle computer’s name of Lan,there are 2 buttons,if button 1 pressed,mark red for disconnected,others mark green for connected,not more than 200 lines(1 line for 1 computer’s name),it is not big I think.


#10

why do you need DataGridView? Why is it not ListView?


#11

I had a project used DataGridView,I really don’t know what’s the difference between them,when this project started,I simply chose the DataGridView to handle data.


#12
try (destroydialog DataGridViewRol) catch()
rollout DataGridViewRol "DataGridView" width:206
(  	
	local dot_color = (dotnetclass "System.Drawing.Color")
	fn make_dot_color rgb = 
	(
		dot_color.FromARGB rgb.r rgb.g rgb.b
	)
	
	dotnetcontrol dgv "DataGridView" width:206 height:660 pos:[1,0] align:#center
	button change_color_bt1 "Change Color1" width:188 align:#left offset:[-4,0] 
	button change_color_bt2 "Change Color2" width:188 align:#left offset:[-4,0]
	button change_color_bt3 "Reset Colors" width:188 align:#left offset:[-4,0]
	
	fn resetRowColors = 
	(
		for k=0 to dgv.rows.count-1 do dgv.rows.item[k].DefaultCellStyle.BackColor = make_dot_color (random white blue)
	)
	
	on change_color_bt1 pressed do
	(
		resetRowColors()
		for k=0 to dgv.rows.count-1 do dgv.rows.item[k].DefaultCellStyle.BackColor = make_dot_color (if mod k 2 == 0 then red else (color 228 228 228))
	)
	on change_color_bt2 pressed do
	(
		resetRowColors()
		for k=0 to dgv.rows.count-1 do dgv.rows.item[k].DefaultCellStyle.BackColor = make_dot_color (if mod k 2 == 1 then green else (color 227 227 227))
	)	
	on change_color_bt3 pressed do
	(
		resetRowColors()
		for k=0 to dgv.rows.count-1 do dgv.rows.item[k].DefaultCellStyle.BackColor = make_dot_color (color 229 229 229)
	)	
	on DataGridViewRol open do
	(
		 
		dgv.Dock = dgv.Dock.Fill
		dgv.RowHeadersVisible = false 			
		dgv.columns.add (dotnetobject "DataGridViewCheckBoxColumn")
				
		dgv.SelectionMode = dgv.SelectionMode.FullRowSelect
		
		dgv.RowCount = 100
		dgv.ColumnCount = 2
		
		dgv.clearselection()
		change_color_bt1.pressed()
	)
 )
 createdialog DataGridViewRol

solution N1:

it’s a trick where you must overwrite all rows with exactly different color


#13

Awesome!Works,but why it works?I don’t understand the reason.It it a bug?


#14

there is something wrong with messages…
DataGridView is ‘too smart’ control (it was designed for minimum redrawing and updating).


#15

OK.anyway,thanks for great help!


#16

here is better solution:

try (destroydialog DataGridViewRol) catch()
rollout DataGridViewRol "DataGridView" width:216
(  	
	local dot_color = (dotnetclass "System.Drawing.Color")
	fn make_dot_color rgb = 
	(
		dot_color.FromARGB rgb.r rgb.g rgb.b
	)

	fn makeCellStyle back_col = 
	(
		local style = dotnetobject "DataGridViewCellStyle"
		style.BackColor = make_dot_color back_col
		style
	)
	
	local grn_style = makeCellStyle green
	local red_style = makeCellStyle red
	local org_style = makeCellStyle (color 128 128 128)
	
	dotnetcontrol dgv "DataGridView" width:216 height:660 pos:[1,0] align:#center
	button change_color_bt1 "Change Color1" width:198 align:#left offset:[-4,0] 
	button change_color_bt2 "Change Color2" width:198 align:#left offset:[-4,0]
	button change_color_bt3 "Reset Colors" width:198 align:#left offset:[-4,0]
	
	on change_color_bt1 pressed do
	(		
		for k=0 to dgv.rows.count-1 do 
		(
			for i=0 to dgv.rows.item[k].cells.count-1 do dgv.rows.item[k].cells.item[i].Style = (if mod k 2 == 0 then grn_style else red_style)
		)
	)
	on change_color_bt2 pressed do
	(
		for k=0 to dgv.rows.count-1 do 
		(
			for i=0 to dgv.rows.item[k].cells.count-1 do dgv.rows.item[k].cells.item[i].Style = (if mod k 2 == 0 then red_style else grn_style)
		)
	)	
	on change_color_bt3 pressed do
	(
		for k=0 to dgv.rows.count-1 do 
		(
			for i=0 to dgv.rows.item[k].cells.count-1 do dgv.rows.item[k].cells.item[i].Style = org_style
		)
	)	
	on DataGridViewRol open do
	(
		 
		dgv.Dock = dgv.Dock.Fill
		dgv.RowHeadersVisible = false 			
		dgv.columns.add (dotnetobject "DataGridViewCheckBoxColumn")
				
		dgv.SelectionMode = dgv.SelectionMode.FullRowSelect
		
		dgv.RowCount = 100
		dgv.ColumnCount = 2
		
		dgv.clearselection()
		change_color_bt1.pressed()
	)
 )
 createdialog DataGridViewRol

probably it’s the right way of how to change all cells background of a row


#17

Denis,the first solution does not work for my project,I don’t know why,but the second works well,it is better as you said,finally I fixed this issue,I really appreciate your patience and your support!


#18

because it’s a trick, and it doesn’t have to work in general case :wink:
the second solution is correct, taking into account the control’s design.


#19

:ok_hand:
Thanks for professional answer.