I have defined variables as string arrays. I also have a form called form4 and on this form I have 1 textbox and 1 combobox.
I have this code in a class:
public class food
{
public string[] name1 = new string [20];
public string[] name2 = new string [50];
public string[] name3 = new string [40] ;
public string[] name = new string [20];
public string[] type = new string [15];
//private const int total = 11;
public int[] calories_ref;
public int i, i2;
public Form4 form = new Form4();
public food(string[] Name1, string[] Name, string[] Type1, int[] kcal)
{
name1 = Name1;
name = Name;
type = Type1;
calories_ref = kcal;
}
public food()
{
}
private void settypes()
{
type[0] = "Bebidas não alcoólicas";
type[1] = "Bebidas Alcóolicas";
type[2] = "Fruta";
type[3] = "Hidratos de Carbono";
type[4] = "Peixe";
type[5] = "Carne";
type[6] = "Cereais";
type[7] = "Lacticínios";
type[8] = "Óleos/Gorduras";
type[9] = "Leguminosas";
type[10] = "Legumes";
for (int i = 0; i < type.Length; i++)
{
form.comboBox1.Items.Add(type[i]);
}
}
In the settypes() method I define the various types of food, more concretly the food wheel. How can I can use these values as items in the combobox that is in form4?
You can add an array of strings using method AddRange(array[]) from comboBox.
form.comboBox1.Items.AddRange(type);
Here is a void you can use if you want to go beyond just one array.
public void AddToCombo(Array array, ComboBox c)
{
foreach(var a in array)
{
c.Items.Add(a);
}
}
You shouldn't be storing a Form4 object in your food class. Your code as it is creates a brand new Form4 every time the food object is created. As shown in the line:
public Form4 form = new Form4();
This won't actually be shown on screen though as you do nothing else with the form except add items to the ComboBox, which also wouldn't show on the screen.
Even if you were to get it shown on the screen, you will still get an error similar to:
Form4.comboBox1 is inaccessible due to its protection level
This is due to the fact that the ComboBox is created internally with private access modifier. (See http://msdn.microsoft.com/en-us/library/ms173121.aspx for more details).
What you need to do is get your existing Form4 to ask the food object to populate it's ComboBox by passing the ComboBox to a method on the food object similar to this example (in your Form4 code not your food code):
private void Form4_Load(object sender, EventArgs e)
{
food f = new food(); //or however you wanted to create the object
f.AddTypesToComboBox(this.comboBox1);
}
The AddTypesToComboBox method would be defined like this in your food object:
public void AddTypesToComboBox(ComboBox box)
{
for (int i = 0; i < type.Length; i++)
{
box.Items.Add(type[i]);
}
}
Also, at the moment the function won't actually add anything to the ComboBox as your type array is not being filled with data. You need to call settypes(); in the food object's constructors like this:
public food(string[] Name1, string[] Name, string[] Type1, int[] kcal)
{
settypes();
name1 = Name1;
name = Name;
type = Type1;
calories_ref = kcal;
}
public food()
{
settypes();
}
You will need to remove public Form4 form = new Form4(); from your variable declaration section as well as removing the following from your settypes() method:
for (int i = 0; i < type.Length; i++)
{
form.comboBox1.Items.Add(type[i]);
}
Your settypes() should only fill the data into the array, and not try and add it to the ComboBox.
If you want the items to be in the ComboBox just set the array as its datasource. You don't need to loop through the array and add the items one by one. It's a lot less code than the other solutions here.
public void SetTypes()
{
comboBox1.DataSource = new[]{
"Bebidas não alcoólicas",
"Bebidas Alcóolicas",
"Fruta",
"Hidratos de Carbono",
"Peixe",
"Carne",
"Cereais",
"Lacticínios",
"Óleos/Gorduras",
"Leguminosas",
"Legumes"
};
}
Not at my computer at the moment, but this should do it:
foreach(var type in type[])
{
form.comboBox1.Items.Add(type);
}
As simple as this:
public void yourMethodName() {
yourComboBoxName.removeAllItems();
for (YourObjectName object: yourArrayListName) {
yourComboBoxName.addItem(object.getWhatYouWanaGet());
}
}
Your remove the actual item from the list than you add the item you want to add :)
If this is an Array in Class1:
public static string[] session = new string[] { "2023-2024", "2022-2023","2021-2022" };
In C# (Windows Forms):
comboBox1.Items.Clear();
comboBox1.Items.AddRange(Class1.session);
Related
As you see in the title above, i need to run a FOR loop to create 4 plumbers from the default constructor. After they are created (within the FOR loop), change their names, add them to the employee list and display in listbox. So basically, plumbers is actually a list declared in another class called EmployeeList. Wehn i tried changing their names to random ones, i get like an error msg saying 'Index is out of range'. Can someone help me with this?
Form Code
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
//create class-level employee list
EmployeeList plumbers = new EmployeeList();
private void Form1_Load(object sender, EventArgs e)
{
//run a for loop to create 4 plumbers from the default constructor.
for (int i = 0; i < plumbers.Count; i++)
plumbers[i] = new Employee();
//After they are created (within the FOR loop), change their names,
//plumbers[0].Name = "Nicole Fernandez";
//add them to the employee list
//display in listbox
foreach (Employee item in plumbers.Employees)
{
lstDisplay.Items.Add(item.DisplayData());
}
}
Employee List Class Code
class EmployeeList
{
//use private access modifier to create a list of employee
private List<Employee> employees = new List<Employee>();
public List<Employee> Employees
{
get { return employees; }
set { employees = value; }
}
//return the count of the employee list, use lambda operator
public int Count => employees.Count();
//create default constructor
public EmployeeList() { }
//create a method that adds employee sent to the list. No return value
public void AddEmp(Employee emp)
{
employees.Add(emp);//add employee to the list
}
//create employee from data sent. No return value
public void AddEmp(string inName, int inID, decimal inHourlyWage)
{
//declare a variable
Employee emp = new Employee(inName, inID, inHourlyWage);
//call the other AddEmp
AddEmp(emp);
}
//create a method that deletes employee from the list. No return value
public void DeleteEmp(Employee emp) => employees.Remove(emp);
//insert employee at the index
public void InsertEmp(Employee emp, int index) => employees.Insert(index, emp);
//create an indexer
public Employee this[int i]
{ //q12 - indexer property with exception
get
{
if (i < 0 || i >= Count)
throw new ArgumentOutOfRangeException(i.ToString());
return employees[i];
}
set { employees[i] = value; }
}
}
Employee Class Code
class Employee
{
//use auto-implemented property
public int ID { get; set; }
public string Name { get; set; }
public decimal HourlyWage { get; set; }
public decimal TotalPay { get; set; }
//create static integer that starts at 1
private static int NextID = 1;
//create a default constructor with default values
public Employee()
{
ID = NextID++;
Name = "John Doe";
HourlyWage = 15.25m;
TotalPay = 0.0m;
}
//create the custom constructor sending in 3 parameters
public Employee(string inName, int inID, decimal inHourlyWage)
{
Name = inName;//set name, no validation is required
//validate ID is between 1 and 250. if not, set to nextID available
if (inID <= 1 && inID >= 250)
NextID = inID;
//validate hourly wage is between 12.50 and 20. If not, set to 15.25
if (inHourlyWage <= 12.50m && inHourlyWage >= 20.0m)
inHourlyWage = 15.25m;
TotalPay = 0;//set total pay to 0
}
public string DisplayData() => ID + "\t" + Name + "\t" + HourlyWage.ToString("c") + "\t" + TotalPay.ToString("c");
}
First, if you want to create a list of 4 plumbers using a loop, then you need the loop to iterate 4 times. This is normally done by setting the initial counter value to 0, then looping while it is less than the number you want:
for (int i = 0; i < 4; i++)
Also, your plumbers object is of type EmployeeList, but you're trying to access it with an indexer as if it's a List or an Array. Instead, you should use the method you created to add new employees:
// Run a for loop to create 4 plumbers from the default constructor.
for (int i = 0; i < 4; i++)
{
plumbers.AddEmp(new Employee());
}
Since there doesn't appear to be any public method to update an existing plumber, we can just access the Employees list directly to rename the plumbers. There are a couple of ways to do it. One would be to use a loop and use part of the loop counter in the name:
// After they are created (within the FOR loop), change their names
for(int i = 0; i < plumbers.Employees.Count; i++)
{
plumbers.Employees[i].Name = string.Format("Plumber #{0}", i);
}
Another way is to do it by hand, giving each plumber a normal name:
plumbers.Employees[0].Name = "Nicole";
plumbers.Employees[1].Name = "Rufus";
plumbers.Employees[2].Name = "Mark";
plumbers.Employees[3].Name = "John";
Or, if you want to be really fancy, you can generate a list of names (I pulled these from the top baby names of 2016), then for each plumber grab a random name from the list and assign it (and remove it from the list so the plumbers all have unique names):
//After they are created (within the FOR loop), change their names
// Generate a list names
var nameCandidates = new List<string>
{
"Olivia", "Amelia", "Charlotte", "Ava", "Isla", "Arabella", "Aurora",
"Adeline", "Penelope", "Eleanor", "Ezra", "Asher", "Atticus",
"Declan", "Oliver", "Silas", "Milo", "Levi", "Henry", "Wyatt"
};
// Loop through each plumber and choose a random name
var rnd = new Random();
foreach(var plumber in plumbers.Employees)
{
// Choose a random name, assign it, and remove it from candidates
var nameIndex = rnd.Next(nameCandidates.Count);
plumber.Name = nameCandidates[nameIndex];
nameCandidates.RemoveAt(nameIndex);
}
public Class Card
{
}
public partial class Form
{
List<Card> list2 = new List<Card>();
}
public List<Card> insertInList(ref List<Card> list1)
{
foreach(...)
{
list1.Add(instanceOfObject Card)
}
return list2;
}
private void btn_click(...)
{
insertInList(ref list2);
}
Edit 1 As this is my second edit, I would appreciate If somebody can tell me that I am using "ref" modifiers well in order to have list full of elements after calling insertInList() method?
Edit 2 How would You change this example, but to have same list full of elements after insert method call, but If your list is defined in method insertInList?
Edit3 (The Biggest Issue) I have still problem, that I am getting 3 lists (same names as Namespace.Class) in ListBox while I am expecting only 1?
public List<Karta> ubaciUListu(ref List<Karta> Lista1)
{
//List<Karta> Lista11 = new List<Karta>();
foreach (DataGridViewRow row in dataGridView1.Rows)
{
Karta k = new Karta(0,"","");
// k.Id =(int)row.Cells[0].Value;
k.Pojam =(string) row.Cells[1].Value;
k.Opis = (string)row.Cells[2].Value;
Lista1.Add(k);
}
return Lista1;
}
public partial class Form2 : Form
{
List<Karta> nova = new List<Karta>();
public Form2(List<Karta> input)
{
InitializeComponent();
nova = input;
if (nova.Count!=0)
{
lstBox.DataSource = nova;
}
}
Dunno if I'm going the right way about this? The contents of the structure below is defined elsewhere. when I run the code it is just outputting a list of 4 zeros. any help would be greatly appreciated.....
public class NativeMethods
{
public struct FT_DEVICE_LIST_INFO_NODE
{
public uint ID;
public uint LocId;
public string SerialNumber;
public string Description;
}
[DllImportAttribute(#"C:\Users\Brendan\Documents\libMPSSE.dll", EntryPoint = "SPI_GetNumChannels")]
public static extern uint SPI_GetChannelInfo(uint index, ref FT_DEVICE_LIST_INFO_NODE chanInfo);
}
public partial class Form1 : Form
{
List<uint> items = new List<uint>();
public Form1()
{
InitializeComponent();
NativeMethods.FT_DEVICE_LIST_INFO_NODE devlist = new NativeMethods.FT_DEVICE_LIST_INFO_NODE();
for(uint x=0;x<4;x++)
{
index = 0;
items.Add(NativeMethods.SPI_GetChannelInfo(index, ref devlist));
}
listBox.DataSource = items;
}
}
Since you wrote that your structure is defined elsewhere I asume you can't change it.
The usual way to get a custom made display string is to wrap your structure in a minimal class, maybe like this:
class FT_DEVICE_wrapper
{
public FT_DEVICE_LIST_INFO_NODE INFO_NODE { get; set; }
public FT_DEVICE_wrapper(FT_DEVICE_LIST_INFO_NODE data_)
{ INFO_NODE = data_; }
public override string ToString()
{
return string.Format("ID = {0} LocID = {1} SNr = {2} ({3}) ",
INFO_NODE.ID, INFO_NODE.LocId, INFO_NODE.SerialNumber, INFO_NODE.Description);
}
}
Now you can add instances of the wrapper like this:
private void button1_Click(object sender, EventArgs e)
{
FT_DEVICE_LIST_INFO_NODE N1 = new FT_DEVICE_LIST_INFO_NODE();
N1.ID = 1;
N1.LocId = 1001;
N1.SerialNumber = "123-456-00";
N1.Description = "test 01";
FT_DEVICE_wrapper W1 = new FT_DEVICE_wrapper(N1);
listBox1.Items.Add(W1);
}
As you can see the structure's data are displayed in whichever way you format the output string.
And you can access the structure by casting the Items like this
Console.WriteLine( ((FT_DEVICE_wrapper) listBox1.Items[0]).INFO_NODE.Description );
Or, imo a little better like this:
FT_DEVICE_LIST_INFO_NODE node = ((FT_DEVICE_wrapper)listBox1.Items[0]).INFO_NODE;
Console.WriteLine(node.SerialNumber);
You may want to consider looking into ListViews, which support columns; here the way to add the structure would be quite different as you would want to put some of the date fields into separate columns.
If you want to use DataBinding you start by creating a proper List:
List<FT_DEVICE_wrapper> items = new List<FT_DEVICE_wrapper>();
and then replace
listBox1.Items.Add(W1);
by
items.Add(W1);
listBox1.DataSource = items;
Note: By simply adding a ToString method to the original structure you cold also make the structure display fine in the ListBox without being wrapped..
I have in a SearchFlyClass an Arraylist GetFly()
...
public ArrayList GetFly(int tip, string country)
{
...
var list = new ArrayList();
var reader = command.ExecuteReader();
if (reader.HasRows)
{
...
while (reader.Read())
{
decimal nr_zbor = reader.GetDecimal(cod_zbor);
string aeroport = reader.GetString(nume_aeroport);
string companie = reader.GetString(nume_companie);
list.Add(nr_zbor);
list.Add(companie);
list.Add(aeroport);
}
}
...
and I wish to put in Form1.cs the list in listview by columns[zbor(colZbor),airport(colAirport),company(colCompany)], but I don't now how
private SearchFlyClass searchFly = new SearchFlyClass();
private ArrayList fly = new ArrayList();
...
private void ShowResultFlySearch(int direction, string country)
{
fly = searchFly.GetFly(direction, country);
for (int count = 0; count < fly.Count; count++)
{
string zbor = fly[0].ToString();
string companie = fly[1].ToString();
string aeroport = fly[2].ToString();
ListViewItem searchlist = new ListViewItem();
searchlist.Items.Add(new ListViewItem(elem));
}
}
can someone help me, please?
First you have to put ListView to View mode details, which you do with following code (it is also possible with setting View property in designer):
ListView listView = new ListView();
listView.View = View.Details;
Then you have to assign columns to the listView (can also be done in designer):
listView.Columns.Add("zbor");
listView.Columns.Add("airport");
listView.Columns.Add("company");
After this you have to assign other columns to ListViewItem subitems, by modifying your function:
private void ShowResultFlySearch(int direction, string country)
{
fly = searchFly.GetFly(direction, country);
for (int count = 0; count < fly.Count; count++)
{
string zbor = fly[0].ToString();
string companie = fly[1].ToString();
string aeroport = fly[2].ToString();
ListViewItem listViewItem = new ListViewItem(zbor);
listViewItem.SubItems.Add(airport);
listViewItem.SubItems.Add(companie);
listView.Items.Add (listViewItem);
}
}
The function assumes that it is in Form1.cs and that you have listView variable instantized as class variable of type ListView. Basics of C# and object oriented programming.
There are lots of issues with this code. Firstly, is there any reason that you're using ArrayList instead of the generic collection types? E.g. List<T>
Secondly, I would create a type to store all of the related data for one instance of your entity, rather than putting the column values for the entity into an untyped collection.
Thirdly, your aren't referencing count anywhere in your for loop - presumably because the query is returning a single entity, and therefore the for loop is redundant because you know the number of items returned for a single entity. You are also using a variable elem which doesn't seem to have been defined.
Updated
Define a type that describes your entity:
public class Flight
{
public decimal Code { get; set; }
public string Company { get; set; }
public string Airport { get; set; }
}
Change your method to return an instance of your entity:
public Flight GetFlight(int tip, string country)
Create a new instance to return from the method and populate it from your database query result:
var flight = new Flight();
flight.Code = reader.GetDecimal(cod_zbor);
flight.Airport = reader.GetString(nume_aeroport);
flight.Company = reader.GetString(nume_companie);
return flight;
Now your other method can use the updated method:
var flight = searchFly.GetFlight(...);
// access flight properties here
This assumes that your query returns a single entity. If it returns a collection, then you can use List<Flight> or IEnumerable<Flight> as your return type as appropriate.
Sorry for my bad English :(.
Hi, how do I add the items to a ListView that I've put in a List?
I've tried this:
listView1.Items.Add(pluginContainer);
But this doesn't seem to work :(.
I can't make a foreach loop because then it will take like 10 seconds for the ListView to be filled (I'm talking about 5000+ items).
This fixed it:
listView1.Items.AddRange(pluginContainer.ToArray());
If the items in your list are all of type ListViewItem, you can use AddRange. If they're not, you're going to have to either make ListViewItems out of them, or use a for loop.
In either case, you should strive to improve the performance of a ListView during addition of items, by first calling SuspendLayout on it. After you've added all its items, call ResumeLayout.
Try this:
public enum State
{
AL, GA, FL, SC, TN, MI
}
public class Person
{
public int ID { get; set; }
public string Name { get; set; }
public State State { get; set; }
// Converts properties to string array
public string[] ToListViewItem()
{
return new string[] {
ID.ToString("00000"),
Name,
State.ToString() };
}
}
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
//Setup list view column headings and widths
listView1.Columns.Add("ID", 48);
listView1.Columns.Add("Name", 300);
listView1.Columns.Add("State", 48);
}
protected override void OnLoad(EventArgs e)
{
base.OnLoad(e);
// Create a list
List<Person> list = new List<Person>();
// Fill in some data
list.Add(new Person() { ID=1001, Name="John", State=State.TN });
list.Add(new Person() { ID=1002, Name="Roger", State=State.AL });
list.Add(new Person() { ID=1003, Name="Samantha", State=State.FL});
list.Add(new Person() { ID=1004, Name="Kara", State=State.MI});
// Fill in ListView from list
PopulateListView(list);
}
void PopulateListView(List<Person> list)
{
listView1.SuspendLayout();
for(int i=0; i<list.Count; i++)
{
// create a list view item
var lvi = new ListViewItem(list[i].ToListViewItem());
// assign class reference to lvi Tag for later use
lvi.Tag = list[i];
// add to list view
listView1.Items.Add(lvi);
}
//This adjust the width of 1st column to fit data.
listView1.AutoResizeColumn(0, ColumnHeaderAutoResizeStyle.ColumnContent);
listView1.ResumeLayout();
}
}