Unselect all rows in datagridview - c#

I have two datagridviews, and when I click to one of them, I would like to deselect all selection in the second datagridview, I tried this, but nothing works:
firstItemsDataGridView.ClearSelection();
firstItemsDataGridView.CurrentCell = null;
not working,
firstItemsDataGridView.ClearSelection();
if (firstItemsDataGridView.Rows.Count > 0)
firstItemsDataGridView[1, 0].Selected = true;
firstItemsDataGridView.CurrentCell = null;
firstItemsDataGridView.ClearSelection();
foreach (DataGridViewRow item in firstItemsDataGridView.Rows) {
item.Selected = false;
foreach (DataGridViewCell itemCell in firstItemsDataGridView.Columns) {
itemCell.Selected = false;
}
}
not working,
firstItemsDataGridView.Rows[0,-1].Selected = true;
not working too.
I have set selecting mode to full row selection, and I have no idea how to achieve my goal. thanks a lot!

dataGridView1.ClearSelection();
Should work. Maybe you have code that auto selects rows which is triggered?

An answer at NullSkull solved the problem for me which was that the cell at row 0, column 0 for the datagridview control was always selected on form load, and could not be deselected despite calling ClearSelection within the form's constructor method. I just had to call ClearSelection in the Form_Load event.
http://www.nullskull.com/q/10066166/how-to-deselect-the-first-row-when-the-form-i-loaded-in-datagridview-in-windows-application.aspx

Since there is no answer, and I used this answer in other posts and i ran into the same issue of first row being selected and deselecting wasn't possible:
Color blue = ColorTranslator.FromHtml("#CCFFFF");
Color red = ColorTranslator.FromHtml("#FFCCFF");
Color letters = Color.Black;
foreach (DataGridViewRow r in datagridIncome.Rows)
{
if (r.Cells[5].Value.ToString().Contains("1")) {
r.DefaultCellStyle.BackColor = blue;
r.DefaultCellStyle.SelectionBackColor = blue;
r.DefaultCellStyle.SelectionForeColor = letters;
}
else {
r.DefaultCellStyle.BackColor = red;
r.DefaultCellStyle.SelectionBackColor = red;
r.DefaultCellStyle.SelectionForeColor = letters;
}
}
This is a small trick, the only way you can see a row is selected, is by the very first column (not column[0], but the one therefore). When you click another row, you will not see the blue selection anymore, only the arrow indicates which row have selected.
SOLUTION:
i found out why my first row was default selected and found out how to not select it by default.
By default my datagridview was the object with the first tab-stop on my windows form. Making the tab stop first on another object (maybe disabling tabstop for the datagrid at all will work to) disabled selecting the first row

Just use:
dgvName.ClearSelection();

I tried this and it's working for me:
for (int i = 0; i < dataGridView1.Rows.Count;i++)
{
dataGridView1.Rows[i].Selected = false;
}

Make sure all the rows are deselected (dataGridView.Rows[...].Selected = false)
Row zero defaults to selected, so set dataGridView.Rows[0].Selected = false when opening the DataGridView and as long as the other options are set so the user can't select, then you will have, and maintain, nothing selected.

// no selection in dgv at the begening
dgv.FirstDisplayedCell = null;
dgv.ClearSelection();
// try this it is working !

If your using WPF and want to maintain a MVVM design pattern you can bind both selected items to the same property so when you select one the other will automatically be deselected.
try something like this
public class SingletonClass
{
private static SingletonClass _Instance;
public static SingletonClass Instance
{
get
{
if (_Instance == null)
_Instance = new SingletonClass();
return _Instance;
}
} // End Property Instance
private object _SelectedItem;
public object SelectedItem
{
get { return _SelectedItem; }
set { _SelectedItem = value; }
} // End Selected Item
}
<DataGrid Name="Datagrid1" SelectedItem="{Binding Source={x:Static Const:SingletonClass.Instance},Path=SelectedItem,IsAsync=True}">
<DataGrid Name="Datagrid2" SelectedItem="{Binding Source={x:Static Const:SingletonClass.Instance},Path=SelectedItem,IsAsync=True}">
*I only used a singleton class because this will work across different views in different instances, you can use a regular class if your in the same view.
Please note the IsAsync=True on the xmal, if you plan on using a singleton class across diffrent views it will not work without it.

As said #Taw in subcomments to top answer - "Don't call it too soon!".
In my case default behavior not works at all. My case - datagrid in tab of tabControl and it did not work if that tab not shown before!
That hack works like a charm :
AnyTabControl.SelectedTab = FirsTab;
gridModules.ClearSelection(); //placed at first tab
AnyTabControl.SelectedTab = SecondTab; //that tab i would like to show first
As a result : second tab displayed to user, and when he clicked to first - selection will not appear.

Related

ListBox Items Disappear

I currently have a ListBox (called wafersListBox) bounded to an ArrayList of a certain object type (called wafers). When I want to add to the ListBox dynamically, I use the following code:
wafersListBox.DataSource = null;
wafersListBox.DataSource = wafers;
wafersListBox.Refresh();
This successfully changes the items in the ListBox, but all of the items disappear (they're still there and can be selected, but the user just can't see them).
Any ideas on how to fix this?
UPDATE:
This is my Wafer class:
public class Wafer
{
public string maID;
public string MID
{
get
{
return maID;
}
set
{
maID = value;
}
}
public Wafer(string m)
{
maID = m;
}
}
This is the code that I call, it adds a copy of the currently selected item to the listbox:
Wafer w = wafersListBox.SelectedItem as Wafer;
wafers.Add(w);
wafersListBox.DataSource = null;
wafersListBox.DisplayMember = "MID";
wafersListBox.DataSource = wafers;
wafersListBox.Refresh();
You should probably tell the wafersListBox what property to use as it's caption.
Do it like this;
wafersListBox.DisplayMember = "PropertyNameThatYouWantToShow";
Sorry - I'm not able to add an additional comment, which would have been preferable over writing a new "answer" but do you see any difference if you switch the position of the lines as below?
Wafer w = wafersListBox.SelectedItem as Wafer;
wafers.Add(w);
wafersListBox.DataSource = null;
wafersListBox.DataSource = wafers;
wafersListBox.DisplayMember = "MID";
wafersListBox.Refresh();
One other thing I just came across on a different SO posting (ListBox doesn't show changes to DataSource):
"There is also a bug in the list box which can cause this problem. If you set the SelectionMode to None this problem appears.
As a work around I set the selection mode to One and then back to None when updating the datasource."

Why does the ListView refuse to display its columns, items, and subitems (shows only Group)?

The ListView seems to be as cantankerous as a polecat and as temperamental as a [elided by the P.C. police]
With help from - and others, I was able to get a ListView working just as I wanted
it to
(http://stackoverflow.com/questions/11423537/how-to-add-subitems-to-a-listview).
Now I'm converting that simple demo for use in a real app.
I create the columns in the form's Load event:
listViewGroupsItems.Columns.Add(colHeadName);
listViewGroupsItems.Columns.Add(colHeadRate);
...but they don't display. However, there is a blank line above my first item. So why are no text values being displayed. Are they "there" but invisible? Why would they get wiped out?
Anyway, what I want to see is:
column1Title column2Title
Group1Name
Item subitem
Item subitem
Group2Name
Item subitem
Group1Name
Item subitem
Item subitem
Item subitem
Item subitem
...but what I actually see is just:
[blank line]
Group1Name
...that's it!
The ListView's View property is set to Details; otherwise, all of the properties are the default values.
My listview code is:
private void AddGroupsAndItems() {
Dictionary<string, string> GroupsDict = PlatypusData.GetGroupsForTopLevel(Convert.ToInt32(labelTopLevel.Tag));
int currentGroup = 0;
foreach (KeyValuePair<string, string> entry in GroupsDict) {
string GroupNumber = entry.Key;
string GroupName = entry.Value;
listViewGroupsItems.Groups.Add(new ListViewGroup(GroupName, HorizontalAlignment.Left));
Dictionary<string, string> ItemsDict = PlatypusData.GetItemsForGroup(GroupNumber);
foreach (KeyValuePair<string, string> itemEntry in ItemsDict) {
string itemID = itemEntry.Key;
string itemName = itemEntry.Value;
ListViewItem lvi = new ListViewItem(string.Format("{0} ({1})", itemName, itemID));
lvi.SubItems.Add(PlatypusData.GetDuckbillNameForItemId(itemID));
listViewGroupsItems.Items.Add(lvi);
listViewGroupsItems.Groups[currentGroup].Items.Add(lvi);
}
currentGroup++;
}
}
UPDATE
I changed my code in the form's Load event from:
var colHeadName = new ColumnHeader { Text = Resources.RateRequestForm_RateRequestForm_Load_Billing_Account_Client, Width = 160 };
var colHeadRate = new ColumnHeader { Text = Resources.RateRequestForm_RateRequestForm_Load_RatePlan_ID, Width = 120 };
listViewCustomerBillAccountsClients.Columns.Add(colheadName); //colHeadName);
listViewCustomerBillAccountsClients.Columns.Add(colheadRate); //colHeadRate);
...to:
ColumnHeader colheadName = new ColumnHeader();
ColumnHeader colheadRate = new ColumnHeader();
listViewCustomerBillAccountsClients.Columns.Add(colheadName);
listViewCustomerBillAccountsClients.Columns.Add(colheadRate);
...and it made no difference at all.
It would seem that the ColumnHeader constructor should be able to take a string of what it should display, but even when I do that:
ColumnHeader colheadName = new ColumnHeader("This");
ColumnHeader colheadRate = new ColumnHeader("That");
...there is still no change (according to Intellisense or whatever it's called, the string arg is an ImageKey, but I thought I'd try just out of thoroughness/frustration.
Late to the party, but I've just spent some time trying to solve a similar problem. The answer I found was that when clearing the list before filling, you must use
listviewGroupItems.Items.Clear();
not
listviewGroupItems.Clear();
The ListView.Clear() method clears everything from the control--including the columns
I had the same issue today. I had coded listView.Clear() as user2867342 mentioned. I needed to change that to listView.Items.Clear(), but that did not make the columns appear. The columns were there, and I could click on them and resize them, but they were completely blank.
I had a ListView set to Details mode. I also had set the OwnerDraw property to true, because I wanted to paint my own progress bar column. MSDN says the following about the OwnerDraw property (emphasis mine):
A ListView control is normally drawn by the operating system. In order
to customize the appearance of ListView items, subitems, and column
headers, set the OwnerDraw property to true and provide a handler for
one or more of the following events: DrawItem, DrawSubItem,
DrawColumnHeader. This is called owner drawing. When the View property
is set to View.Details, all three events occur; otherwise, only the
DrawItem event occurs.
I had to implement the DrawColumnHeader event. In my case, the defualt worked fine, so the method sets the DrawDefault event parameter to true. After implementing this event handler, the column headers appeared correctly:
...Windows.Forms designer code...
listView.DrawColumnHeader += new DrawListViewColumnHeaderEventHandler(this.listView_DrawColumnHeader);
...
private void listView_DrawColumnHeader(object sender, DrawListViewColumnHeaderEventArgs e)
{
e.DrawDefault = true;
}
You're missing column headers in your code. (fixed)
Per the MSDN:
"If your ListView control does not have any column headers specified and you set the View property to View.Details, the ListView control will not display any items. If your ListView control does not have any column headers specified and you set the View property to View.Tile, the ListView control will not display any subitems."
Granted, you'll probably need to make more adjustments than what you see in my SS, but it at least answers your question as to why you are getting blanks.
Edit (Changed lines, although changing them back to your code didn't skew my successful results):
lvi.Group = listViewGroupsItems.Groups[currentGroup];
listViewGroupsItems.Items.Add(lvi);
One more thing to check I just found:
OwnerDraw must be false.
Copy & Paste from previous project and forgot that I used OwnerDraw

Infragistics UltraGrid: GroupBy row ForeColor changes when clicked

Using Infragistics UltraGrid in WinForms in C#:
I am conditionally changing the color of the ForeColor of some GroupByRows on a grid. When the user clicks the row, the color changes back to the active/selected/hot tracked/whatever color until they click on something else. I'd like the text color of the rows that I have conditionally colored to never change. Here's how I'm setting the color:
Row.Appearance.ForeColor = System.Drawing.Color.Orange;
Any idea how to make it stick even when the row is clicked?
Thanks!
This can be done with a draw filter to set the fore color of the description since this would apply at all times.
A simple example is the following draw filter which will make all group by rows that have an integer value that is even orange:
public class GroupByRowDrawFilter:IUIElementDrawFilter
{
public bool DrawElement(DrawPhase drawPhase, ref UIElementDrawParams drawParams)
{
GroupByRowDescriptionUIElement element = (GroupByRowDescriptionUIElement)drawParams.Element;
if (element.GroupByRow.Value is int)
{
int value = (int)element.GroupByRow.Value;
if (value % 2 == 0)
{
drawParams.AppearanceData.ForeColor = Color.Orange;
}
}
return false;
}
public DrawPhase GetPhasesToFilter(ref UIElementDrawParams drawParams)
{
if (drawParams.Element is GroupByRowDescriptionUIElement)
return DrawPhase.BeforeDrawElement;
return DrawPhase.None;
}
}
To apply the draw filter use the following line of code:
this.ultraGrid1.DrawFilter = new GroupByRowDrawFilter();
Note that this approach requires that the condition be in the draw filter. If this doesn't work for you, you could modify your logic where you are currently setting the ForeColor to set the Tag property of the GroupByRow instead and then check the Tag property in the draw filter to determine if you need to apply your logic.
I think you should also change the
grd.DisplayLayout.Override.SelectedRowAppearance.ForeColor = System.Drawning.Color.Orange;
or better
grd.DisplayLayout.Override.GroupByRowAppearance.ForeColor = System.Drawning.Color.Orange;
sorry, but I'm away from a PC where I can test.
Usually these properties could be changed effectively in the InitializeLayout event where you get the Layout object inside the event arguments.
e.Layout.Override.GroupByRowAppearance.ForeColor = Color.Orange;
EDIT: At the moment the only solution that I have found is the following
private void grd_BeforeRowActivate(object sender, RowEventArgs e)
{
// You need to add the additional logic required by you to
// determine which rows need to have the forecolo changed...
if (e.Row.IsGroupByRow == true)
grd.DisplayLayout.Override.ActiveRowAppearance.ForeColor = Color.Orange;
else
grd.DisplayLayout.Override.ResetActiveRowAppearance();
}
Infragistics says:
the "Ability to have active and selected conditional appearances for the GroupByRows" has been determined to be a new product idea

How to disable only the checkboxes (and not the full checkedboxlist) of devexpress?

In non-edit mode, I need the user to be able to browse the list (scroll etc.) but not be able to select the checkboxes.
If I do checkedboxlist.enabled = false, then the whole list becomes disabled. Only I need to disable checkboxes so that user doesn't interact (in edit way) in non-edit mode.
EDIT
I just assign the list of strings to the checkedboxlist's datasource.
this.UserSelectedMsgTypes.DataSource = userSelectedMsgs;
this.UserAvailableMsgTypes.DataSource = availableMsgTypeList;
currently enabling/disabling whole list by doing
this.UserSelectedMsgTypes.Enabled = true/false;
this.UserAvailableMsgTypes.Enabled = true/false;
I tried #James solution earlier, doesnt work. Because somehow the 'ItemCount' is 0 even though there are items. in the datasource it shows that there are 6 items, but in list it shows 0.
Try this:
foreach (DevExpress.XtraEditors.Controls.CheckedListBoxItem item in checkedListBoxControl1.Items)
{
item.Enabled = false;
}
It's a bit of a dirty work around but how about this?
private IEnumerable<DevExpress.XtraEditors.Controls.CheckedListBoxItem> GetCheckItems(string[] myStringArray)
{
foreach(string s in myStringArray)
{
DevExpress.XtraEditors.Controls.CheckedListBoxItem item = new DevExpress.XtraEditors.Controls.CheckedListBoxItem();
item.Description = s;
yield return item;
}
}
Call with:
checkedListBoxControl1.Items.AddRange(GetCheckItems(new string[] {"test1","test2","test3"}).ToArray());
Then apply the first answer with the foreach loop (or set the ENabled = false in the GetCheckItems method).

How can I make a specific TabItem gain focus on a TabControl without click event?

How can I tell my TabControl to set the focus to its first TabItem, something like this:
PSEUDO-CODE:
((TabItem)(MainTabControl.Children[0])).SetFocus();
How about this?
MainTabControl.SelectedIndex = 0;
this.tabControl1.SelectedTab = this.tabControl1.TabPages["tSummary"];
I've found it's usually a best practice to name your tabs and access it via the name so that if/when other people (or you) add to or subtact tabs as part of updating, you don't have to go through your code and find and fix all those "hard coded" indexes. hope this helps.
I realise this was answered a long time ago, however a better solution would be to bind your items to a collection in your model and expose a property that selected item is bound to.
XAML:
<!-- MyTemplateForItem represents your template -->
<TabControl ItemsSource="{Binding MyCollectionOfItems}"
SelectedItem="{Binding SelectedItem}"
ContentTemplate="{StaticResource MyTemplateForItem}">
</TabControl>
Code Behind:
public ObservableCollection<MyItem> MyCollectionOfItems {
get;
private set;
}
private MyItem selectedItem;
public MyItem SelectedItem{
get { return selectedItem; }
set {
if (!Object.Equals(selectedItem, value)) {
selectedItem = value;
// Ensure you implement System.ComponentModel.INotifyPropertyChanged
OnNotifyPropertyChanged("SelectedItem");
}
}
}
Now, all you have to do to set the item is:
MyItem = someItemToSelect;
You can use the same logic with the SelectedIndex property, further, you can use the two at the same time.
This approach allows you to separate your model correctly from the UI, which could allow you to replace the TabControl with something else down the line but not requiring you to change your underlying model.
Look at the properties for the tab control...
Expand the TabPages properties "collection"...
Make note of the names you gave the members.
ie. a tab control called tabMain with 2 tabs called tabHeader and tabDetail
Then to select either tab...You have to set it with the tabname
tabMain.SelectedTab = tabHeader;
tabControl1.SelectedTab = item;
item.Focus();
Basically all of the answers here deal with SELECTION, which does not answer the question.
Maybe that is what OP wanted, but the question very specifically asks for FOCUS.
TabItem item = (TabItem)MainTabControl.Items[0];
// OR
TabItem item = (TabItem)MainTabControl.SelectedItem;
// Then
item.Focus();
tabControl.SelectedItem = tabControl.Items[0];
If you have a Tabcontroller named tabControl you could set the selectedIndex from different methods, i use following methods mostly.
codebehind:
tabControl.SelectedIndex = 0; // Sets the focus to first tabpanel
clientside:
First, put the following javascript in your aspx/ascx file:
<script type="text/javascript">
function SetActiveTab(tabControl, activeTabIndex) {
var activeTab = tabControl.GetTab(activeTabIndex);
if(activeTab != null)
tabControl.SetActiveTab(activeTab);
}</script>
Then add following clientside event to prefered controller:
OnClientClick="function(s, e) { SetActiveTab(tabControl, 0);
it's better to use the following type of code to select the particular
item in the particular tab...
.
private void PutFocusOnControl(Control element)
{
if (element != null)
Dispatcher.BeginInvoke(System.Windows.Threading.DispatcherPriority.Input,
(System.Threading.ThreadStart)delegate
{
element.Focus();
});
}
And in calling time... tabcontrol.isselected=true;
PutFocusOnControl(textbox1);
will works fine...
Private Sub TabControl1_SelectedIndexChanged(sender As Object, e As EventArgs) Handles TabControl1.SelectedIndexChanged
'MsgBox(TabControl1.SelectedIndex)
If TabControl1.SelectedIndex = 0 Then
txt_apclntFrstName.Select()
Else
txtApplcnNo.Select()
End If
End Sub
It worked for me to set focus to the last tab just after I open it:
//this is my assignment of the collection to the tab control
DictTabControl.DataContext = appTabs.DictTabs;
//set the selected item to the last in the collection, i.e., the one I just added to the end.
DictTabControl.SelectedItem = DictTabControl.Items[(DictTabControl.Items.Count-1)];

Categories