I have one form in a Windows application as per below image:
I try to use this code to display text in comboBox in "Designer.cs":
this.cmbLanguage.FormattingEnabled = true;
this.cmbLanguage.Items.AddRange(new object[] {
Language.LSelectLang.LANGUAGE_ENGLISH, //"English",
"Chinese_TC",
"Chinese_SC",
Language.LSelectLang.LANGUAGE_GERMAN, //"German",
Language.LSelectLang.LANGUAGE_FRENCH, //"French",
Language.LSelectLang.LANGUAGE_JAPANESE, //"Japanese",
Language.LSelectLang.LANGUAGE_SPANISH, //"Spanish",
Language.LSelectLang.LANGUAGE_HINDI}); //"Hindi"});
It's OK with it, but I want to also pass a value type to access specific text display in combo box.
So, how to pass that in my combo box?
Unluckily, Win Form does not define ListItem like Web, but you can define your own class, then override ToString method:
public class YourItem<T>
{
public string Text { get; set; }
public T Value { get; set; }
public override string ToString()
{
return Text;
}
}
Then you can use:
var item = new YourItem<string>() {
Text = "text",
Value = "value"
};
cmbLanguage.Items.Add(item);
To access value:
var selectedItem = (YourItem<string>) cmbLanguage.SelectedItem;
var value = selectedItem.Value;
Related
How can I show Text in ComboBox when no item selected in Windows Application using LINQ C#
Here is my code how I get all rooms.... in Combobox.
private void LoadRoom()
{
try
{
db = new HotelEntities();
// cmbProvince.Text = "";
var Room = (from u in db.Room
select new { u.RoomId, u.RoomNumber }).ToList();
cmbRoom.Text = ".. Select.."; // This one do not working.
cmbRoom.DisplayMember = "RoomNumber";
cmbRoom.ValueMember = "RoomId";
cmbRoom.DataSource = Room;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
Thank you!
If you set the DataSource of a combobox, a currencymanager is used on the background and its position is selected (the first item).
Instead of setting DataSource, try adding the items:
cmbRoom.Items.AddRange(Room);
NB, setting Text as a placeholder will not work if an item is chosen and cleared later, unless you add an extra check (in TextChanged or SelectedIndexChanged)
Fast solution
Create a source class for your ComboItems, with (at least) the properties to Display and the inner value of the property. If you create a generic class you can use it for all your combo boxes.
class ComboDisplay<TSource>
{
public string Display {get; set;}
public TSource Value {get; set;}
}
cmbRoom.DisplayMember = nameof(ComboDisplay.Display);
cmbRoom.ValueMember = nameof(ComboDisplay.Value);
When you create the data source for your combobox, make sure you add a default value. In the example below I assume that you want to select items of type Room in your combo:
IEnumerable<Room> availableRooms = myDbContext.Rooms
.Where(room => room.IsAvailable)
.Select(room => new ComboDisplay<Room>
{
Display = room.Name,
Value = new Room
{
Id = room.Id,
...
},
})
// add a dummy value if nothing is selected
.Concat(new Room[]
{
Display = "Please select a room",
Value = null, // meaning: nothing selected
});
After selection, use comboBox1.SelectedValue to get the selected Room, or null if nothing is selected.
Create a Special Combobox class
If you have to use this regularly, consider creating a generic sub class of ComboBox that can display items of a certain TSource, and will return null if nothing is selected:
class MyComboBox<TSource> : ComboBox
{
public MyComboBox() : base()
{
base.DataSource = this.EmptyList;
base.DisplayMember = nameof(ComboDisplay.Display);
base.ValueMember = nameof(ComboDisplay.Value);
}
private static readonly EmptyItem = new ComboDisplay
{
Display = "Please select a value",
Value = null,
}
Make a property that returns the available combo items. Make sure that the EmptyItem is always in the collection:
public IReadonlyCollection<TSource> ComboItems
{
get {return (IReadOnlyCollection<TSource>)base.DataSource;}
set
{
// TODO: check if the empty element is in your list; if not add it
base.DataSource = value;
}
}
Finally: the function to get the Selected value, or null if nothing is selected:
public TSource SelectedValue
{
get => return (TSource)base.SelectedValue;
set
{
// TODO: check if value is in ComboItems
base.SelectedValue = value;
}
}
What I would like to do is to populate a drop down menu from a database.
First of all I plan to use a combo box.
I have created an object that contains the data that I need to take from the database. The object is as follows
namespace RLMD
{
public class FlashCardLevel
{
private int intFCLId;
private String strFCLName;
public FlashCardLevel(int intFCLId, String strFCLName)
{
this.intFCLId = intFCLId;
this.strFCLName = strFCLName;
}
public int IntFCLId
{
get { return intFCLId; }
set { this.intFCLId = value; }
}
public String StrFCLName
{
get { return strFCLName; }
set { this.strFCLName = value; }
}
}
}
What I need to do is to add a list of items from a database, but for ease of use I have simulated given some sample data.
public List<FlashCardLevel> Rifle(List<FlashCardLevel> fcLevel)
{
fcLevel.Add(new FlashCardLevel(1, "Severe"));
fcLevel.Add(new FlashCardLevel(2, "Moderate"));
fcLevel.Add(new FlashCardLevel(3, "Mild"));
fcLevel.Add(new FlashCardLevel(4, "Slight"));
return fcLevel;
}
I'm calling the method here.
List<FlashCardLevel> fcLevel = new List<FlashCardLevel>();
talkToDatabase.Rifle(fcLevel);
this.comboCardLevel.DataSource = fcLevel;
this.comboCardLevel.DisplayMember = "Name";
this.comboCardLevel.ValueMember = "Value";
The combobox is displaying no information.
I would appreciate any help
Updated:
The DisplayMember Property should be referring to FlashCardLevel (class), Property StrFCLName and ValueMember should be pointing to IntFCLId.
List<FlashCardLevel> fcLevel = new List<FlashCardLevel>();
talkToDatabase.Rifle(fcLevel);
this.comboCardLevel.DataSource = listFromDatabase;
this.comboCardLevel.DisplayMember = "StrFCLName";
this.comboCardLevel.ValueMember = "IntFCLId";
The DisplayMember and ValueMember should point to your properties name.
this.comboCardLevel.DisplayMember = "IntFCLId";
this.comboCardLevel.ValueMember = "StrFCLName";
Is it possible to add to checkedListBox item also value and title
checkedListBox1.Items.Insert(0,"title");
How to add also value?
checkedListBox1.Items.Insert(0, new ListBoxItem("text", "value"));
Try setting the DisplayMember and ValueMember properties. Then you can pass an anonymous object like so:
checkedListBox1.DisplayMember = "Text";
checkedListBox1.ValueMember = "Value";
checkedListBox1.Items.Insert(0, new { Text= "text", Value = "value"})
Edit:
To answer your question below, you can create a class for your item like so:
public class MyListBoxItem
{
public string Text { get; set; }
public string Value { get; set; }
}
And then add them like this:
checkedListBox1.Items.Insert(0, new MyListBoxItem { Text = "text", Value = "value" });
And then you can get the value like this:
(checkedListBox1.Items[0] as MyListBoxItem).Value
I have a combo box that populates data from the database, which, based on a list box selection populates the data within a given list box through an SQL query. Problem is that the display member property wont show. I wont show the back-end sql because that works fine and the list box actually populates just not the display member. So the data in the list box is blank.
Here is the code:
The Combobox method:
private void populateFromMedication()
{
MedicationList medicationItem = new MedicationList();
// if item is selected
if( !( ( Locations )cmbLocationDescriptionList.SelectedItem == null ) )
{
// set location to be the seletect location from the combo
location = ( Locations )cmbLocationDescriptionList.SelectedItem;
List<MedicationList> fromMedicatitionList = new List<MedicationList>();
// retrieve a list of medication from the database
fromMedicatitionList = LocationData.RetrieveMedicationByLocation( location.LocationID, GlobalVariables.SelectedResident.ResidentID );
//bind the list for to the medication list
lstMedicationForCurrentLocation.ItemsSource = fromMedicatitionList;
lstMedicationForCurrentLocation.DisplayMemberPath = "Description";
}
}
On form Initialization:
public FormInitialize()
{
InitializeComponent();
LoadData();
LoadResidentData();
populateFromMedication();
}
MedicationList Class:
public class MedicationList
{
public int MedicationID { get; set; }
public string Description
{
get
{
return Description;
}
set
{
Description = value;
OnPropertyChanged( "Description" );
}
}
}
You need to check that
1) There is a property in MedicationList by the name Description and that OnPropertyChanged is applied on its setter.
string _Description;
public string Description
{
get
{
return _Description;
}
set
{
_Description = value;
OnPropertyChanged("Description");
}
}
For more on OnPropertyChanged read this
2) Try giving Displaymember before providing Itemsource.
I have a ParameterItem class for adding some items to a listbox:
class ParameterItem
{
public string Name { get; set; }
public string Value { get; set; }
public ParameterItem(string name, string value)
{
Name = name;
Value = value;
}
public override string ToString()
{
return Name + " = " + Value;
}
public override bool Equals(object obj)
{
if (obj is ParameterItem)
return (Name == ((ParameterItem)obj).Name);
return false;
}
public override int GetHashCode()
{
return Name.ToLowerInvariant().GetHashCode();
}
}
And you can add items to the listbox using two textboxes (name and value). When you click on an item in the listbox, the textboxes get filled with the name and the value of the ParameterItem. I have the following code to change the contents of the selected ParameterItem in the listbox:
private void btnSaveParameter_Click(object sender, EventArgs e)
{
ParameterItem currentParameter = new ParameterItem(textParameterName.Text,
textParameterValue.Text);
// If we already have the parameter set then edit it.
if (lstbxSetParameters.Items.Contains(currentParameter))
{
((ParameterItem)lstbxSetParameters.SelectedItem).Value = currentParameter.Value;
lstbxSetParameters.;
}
// If it's not set yet then add it to the listbox.
else
{
lstbxSetParameters.Items.Add(currentParameter);
textParameterName.Text = String.Empty;
textParameterValue.Text = String.Empty;
}
}
The problem is, even though I can change the contents of the selected ParameterItem, in the listbox, it still looks like it is not changed.
For example I have a parameter in the list box:
TestParameter = 10
And I change the ParameterItem to
TestParameter = 5
but in the listbox it still looks like
TestParameter = 10
even though it's been changed.
How can I solve this problem? I think the listbox item should call the ToString() method of the ParameterItem again and refresh itself but how?
Or is there a better way to add key value pairs in the listbox?
You can change the selected item by remove it and insert it again.
// If we already have the parameter set then edit it.
if (lstbxSetParameters.Items.Contains(currentParameter))
{
var newItem = new ParameterItem((lstbxSetParameters.SelectedItem as ParameterItem).Name, currentParameter.Value);
var index = lstbxSetParameters.SelectedIndex;
lstbxSetParameters.Items.RemoveAt(index);
lstbxSetParameters.Items.Insert(index, newItem);
lstbxSetParameters.SelectedIndex = index;
}
My solution:
string[] nList = new string[lb.Items.Count];
nList = lb.Items.OfType<string>().ToArray();
nList[lb.SelectedIndex] = newValue;
lb.Items.Clear();
lb.Items.AddRange(nList);
This way instead of changing the selected item (with a lot of problem) I reloaded the Listbox with the item changed in the array.