find a control inside a tabpage that is created with a usercontrol - c#

i have created a usercontrol, then i have a tabcontrol where in there is a tabpage that contains a 2 buttons, when button1 is clicked, it creates a new tabpage and the user control is added to its controls through
tab = new TabPage();
UserControl1 uc = new UserControl1();
tab.Controls.Add(uc);
tab.Name = "0";
tab.Text = tab.Name;
tabControl1.TabPages.Add(tab);
now when i click the button2, it should put text in the textbox inside the usercontrol-tabpage that was just created, i implemented it with this code,
TextBox sel = (TextBox)tabControl1.TabPages["0"].Controls["textBox1"];
sel.Text = "ssss";
but it returns a runtime error, saying that it cannot find the said control, so i tried
TextBox sel = (TextBox)tabControl1.TabPages["0"].Controls[0];
sel.Text = "ssss";
but it still returns a runtime error, saying that the cast usercontrol cannot be applied to textbox. i dont know what that means.. pls help me in this.. i also tried putting in Controls[1] but it returned a runtime error, of which is a OutofBounds exception. i dont know what to do, or how to find the control inside the usercontrol in the tabpage... pls hellp

It's a little bit unclear if the TextBox already exists in the UserControl, so I will assume it does. In that case, you have to reference the UserControl first:
UserControl1 uc1 = tabControl1.TabPages["0"].Controls[0] as UserControl1;
if (uc1 != null) {
TextBox sel = uc1.Controls["textBox1"] as TextBox;
if (sel != null) {
sel.Text = "ssss";
}
}

UserControl uc = NameTabPages.Controls[0] as UserControl; // it's work

Related

Displaying user control in parent form panel

The first line is able to clear the panel but doesnt seem to show the usercontrol in the panel in the parent form.
panel1.Parent.Controls.Clear();
if (panel1.Parent == null)
return;
messagessent uc = new messagessent();
uc.Dock = DockStyle.Fill;
panel1.Parent.Controls.Add(uc);
Why you use panel1.Parent? In this way, you remove all controls not from the panel itself, but from the parent control on which this panel is located.
This action removes the panel itself. And, accordingly, the panel does not have a parent now. The Parent property becomes null.
I suppose you need to write like this:
panel1.Controls.Clear();
messagessent uc = new messagessent();
uc.Dock = DockStyle.Fill;
panel1.Controls.Add(uc);

How to change a form controls using treeview in C#?

I'm using C#, and I want create a form - which is composed of treeview treeview1, a panel panel1 and a button btn1.
In the begining the panel is empty, then a userControl userControl1 will be shown when the user select a node from the tree, and another userControl userControl2 will replace the first whene the user select another specific node , and go on ... as in setting forms
I found a solution here :
How to create an options form in C# Windows Forms?
but it is written i pseudo-code, i try implementing the code, and this what i get:
//on initializing
treeView1.Nodes.Add(new TreeNode());
treeView1.Nodes.Add(new TreeNode());
treeView1.Nodes.Add(new TreeNode());
treeView1.Nodes[0].Tag = new UserControl1();
treeView1.Nodes[1].Tag = new UserControl2();
treeView1.Nodes[2].Tag = new UserControl3();
treeView1.Nodes[0].Text = "user controle1";
treeView1.Nodes[1].Text = "user controle2";
treeView1.Nodes[2].Text = "user controle3";
private void treeView1_AfterSelect(object sender, TreeViewEventArgs e)
{
UserControl currentControl = (UserControl)treeView1.SelectedNode.Tag;
TreeNode currentnode = treeView1.SelectedNode;
if (panel1.Controls != null)
{
panel1.Controls.Clear();
}
if (currentnode.Tag == null)
return;
panel1.Controls.Add((UserControl)currentnode.Tag);
}
and about the usecontrols I add nothing to the code, just controls that i need...
It works, but I am not sure if it is correct, I find other solutions and they add a lot of stuff to both, the user controls and to the main form.
So, what this code need to work properly.

How to delete (remove) space between textboxes after remove some controls?

I'm new working with C# and I'm asking on here because I didn't find a solution searching in google and other questions on SO, I will explain what my example application does:
When I run it it display a form with a textbox by default, this textbox always will be shown, after type some text and press enter it will generate a new textbox and a new button (all the controls even the default textbox are inside a panel), and the new textboxes have the same functionality as the default textbox, when I click on the button generated next to its textbox it removes the button itself and the textbox but after that if I remove some random textboxes it leaves a space between these controls, how can reorganize this content to dont let space between them?
As you can see in the image, can you tell me how can fix this or give me an advice to achieve this? thank you, by the way this is the method I use to generate the buttons and textboxes
private void GenerarTextBox()
{
panelContenedor.VerticalScroll.Value = panelContenedor.VerticalScroll.Minimum;
TextBox tb = new TextBox();
tb.Text = "Prueba " + id;
tb.Name = "txtBox" + id;
tb.KeyDown += new KeyEventHandler(TextBox_Keydown);
Button bt = new Button();
bt.Cursor = Cursors.Hand;
bt.Text = "X";
bt.Name = "btnPrueba" + id;
bt.Click += new EventHandler(ClickBotones);
Point p = new Point(20, 30 * id);
Point pb = new Point(130, 30 * id);
tb.Location = p;
bt.Location = pb;
panelContenedor.Controls.Add(tb);
panelContenedor.Controls.Add(bt);
tb.Focus();
id++;
}
And this to remove the textboxes and the buttons
private void ClickBotones(object sender, EventArgs e)
{
Button bt = sender as Button;
string nombreBoton = bt.Name;
string idBoton = nombreBoton.Substring(9);
string nombreTextBox = "txtBox" + idBoton;
foreach (Control item in panelContenedor.Controls.OfType<Control>())
{
if (item.Name == nombreTextBox)
{
panelContenedor.Controls.Remove(item);
panelContenedor.Controls.Remove(bt);
}
}
}
You could place your dynamic controls on a FlowLayoutPanel. Either directly or grouped together in a Panel or UserControl.
Set the FlowDirection property of the FlowLayoutPanel to TopDown. The FlowLayoutPanel will then arrange your controls automatically. You can also set the WrapContents property to False and AutoScroll to true to make the scroll bar appear.
Alternatively you can use FlowDirection = LeftToRight, place the text box and the button directly on the FlowLayoutPanel and let the child controls wrap (WrapContents = True). In the child controls, a new property FlowBreak appears. It can be set to True for the last control to appear in a row and let the next one wrap independently of the width of the FlowLayoutPanel.
You can also play with the Margin property of the child controls to control their layout in the FlowLayoutPanel as the Location property becomes useless.
The FlowLayoutPanel (as well as the Panel) is available in the Toolbox in the section "Containers".
When you delete the controls, you need to do a recalc of the positions. So when you have added them in sequence, you can go with:
bool repos = false;
Point p;
foreach (Control item in panelContenedor.Controls.OfType<Control>())
{
if (repos)
{
Point tmp = item.Location;
item.Location = p;
p = tmp;
}
if (item.Name == nombreTextBox)
{
panelContenedor.Controls.Remove(item);
panelContenedor.Controls.Remove(bt);
repos = true;
p = item.Location;
}
}

Edit a button by its given name

I am generating x amount of buttons and I give all of them a unique name.
After all those are generated, I want to edit one of them without regenerating them so I was wondering if I could get a component by its name?
I am using WinForms
Yes:
Control myControl = Controls.Find("textBox1");
Now, beware that you have to do proper casting hen found, because Find returns a control.
You can use Controls property of your form (or some container control on your form). With LINQ you can select buttons and then find first button with required name:
var button1 = Controls.OfType<Button>().FirstOrDefault(b => b.Name == "button1");
Or if you want to search child controls recursively
var button1 = Controls.Find("button1", true)
.OfType<Button>()
.FirstOrDefault();
Without LINQ you can use method Find(string key, bool searchAllChildren) of ControlCollection:
Control[] controls = Controls.Find("button1", true);
if (controls.Length > 0)
{
Button button1 = controls[0] as Button;
}
Button btn1 = (Button)(Controls.Find("btnName"));
This will get the required button and will save the button attributes into a new Button btn1
After all those are generated, I want to edit one of them without
regenerating them so I was wondering if I could get a component by its
name?
var myButton = Controls.Find("buttonName", true).FirstOrDefault(); //Gets control by name
if(myButton != null)
{
if (myButton.GetType() == typeof(Button)) //Check if selected control is of type Button
{
//Edit button here...
}
else
{
//Control isn't a button
}
}
else
{
//Control not found.
}
Make sure you add a reference to: linq.

Referencing a dynamically created control?

I know how to create a dynamic control in c#:
TextBlock tb = new TextBlock();
tb.Text = "This is a new textblock";
But how would I reference this newly created control through code?
I browsed the net for a solution, and came across this code:
TextBlock tb = (TextBlock)this.FindName("TB");
tb.Text = "Text property changed";
Every time I create a new control with a name I get an exception:
TextBlock tb = new TextBlock();
tb.Text = "This is a new textblock";
tb.Name = "TB";
"The parameter is incorrect."
What am I doing wrong? Any help would be greatly appreciated.
Thanks in advance.
The Exception "The parameter is incorrect." may be occurring because of the duplicate names of the controls created.
For the dynamic control part : you must be adding that control to some Grid or Stackpanel or something. you can reference that dynamic control by getting the content or children of the parent control.
Like :
TextBlock Tb= new TextBlock();
tb.Text = "Hello";
ContentPanel.Children.Add(Tb);
//to reference :
var content = ContentPanel.Children;
foreach(UIElement uiElem in content)
{
if(uiElem.GetType() == typeof(TextBlock))
{
TextBlock tb = uiElem as TextBlock;
tb.Text = "Hyee";
}
}
Hope, it might help.
(Note: I have written this code directly here and not copied from VS, so please check syntax and spellings.)
Yes you can use reference dynamic controls this way.
But another way is that you can also keep a list of the references when you create the controls.

Categories

Resources