I have two asp:RadioButton controls which are having the same GroupName which essentially makes them mutually exclusive.
My markup:
<asp:RadioButton ID="OneJobPerMonthRadio" runat="server"
CssClass="regtype"
GroupName="RegistrationType"
ToolTip="125"/>
<asp:RadioButton ID="TwoJobsPerMonthRadio" runat="server"
CssClass="regtype"
GroupName="RegistrationType"
ToolTip="200"/>
My intention was to find the tooltip / text of the RadioButton that is checked. I have this code-behind:
int registrationTypeAmount = 0;
if (OneJobPerMonthRadio.Checked)
{
registrationTypeAmount = Convert.ToInt32(OneJobPerMonthRadio.ToolTip);
}
if (TwoJobsPerMonthRadio.Checked)
{
registrationTypeAmount = Convert.ToInt32(TwoJobsPerMonthRadio.ToolTip);
}
I find that code ugly and redundant. (What if I have 20 checkboxes?)
Is there a method that would get the checked RadioButton from a set of RadioButtons with the same GroupName? And if not, what are the pointers on writing one?
P.S: I cannot use a RadioButtonList in this scenario.
You want to do this:
RadioButton selRB = radioButtonsContainer.Controls.OfType<RadioButton>().FirstOrDefault(rb => rb.Checked);
if(selRB != null)
{
int registrationTypeAmount = Convert.ToInt32(selRB.ToolTip);
string cbText = selRB.Text;
}
where radioButtonsContainer is the container of the radiobuttons.
Update
If you want to ensure you get RadioButtons with the same group, you have 2 options:
Get them in separate containers
Add the group filter to the lamdba expression, so it looks like this:
rb => rb.Checked && rb.GroupName == "YourGroup"
Update 2
Modified the code to make it a little more fail proof by ensuring it won't fail if there's no RadioButton selected.
You may try writing down a similar method to the one below:
private RadioButton GetSelectedRadioButton(params RadioButton[] radioButtonGroup)
{
// Go through all the RadioButton controls that you passed to the method
for (int i = 0; i < radioButtonGroup.Length; i++)
{
// If the current RadioButton control is checked,
if (radioButtonGroup[i].Checked)
{
// return it
return radioButtonGroup[i];
}
}
// If none of the RadioButton controls is checked, return NULL
return null;
}
Then, you can call the method like this:
RadioButton selectedRadio =
GetSelectedRadioButton(OneJobPerMonthRadio, TwoJobsPerMonthRadio);
It will return the selected one (if there is) and it will work for no matter how many radio buttons you have. You can rewrite the method, so that it returns the SelectedValue, if you wish.
Related
Is it possible to store in the same array - list of different type elements declaring in the same array different property value (bool)? For exampe list of those elements:
GV1_BTNEdit.Visible = false;
GV1_BTNCancel.Visible = true;
GV1.Columns[3].Visible = true;
GV1.Columns[5].Visible = true;
GV1.Columns[4].Visible = true;
Lbl1_GV1.Visible = true;
Edit: (pseudo-code)
This is how funcionality should look like:
Declares a list/array of elements with a simultaneous declaration of parameters / properties of these elements:
list/element array (list_name)
{
textbox1.visible = true;
label1.visible = false;
button1.visible = true;
}
Calling a list/array, i.e. simultaneous assignment to the elements of the list - the property resulting from their declaration in the list:
list_name[];
Calling the list with the same property change, i.e. simultaneous assigning to all elements of the list the property visible = false:
list_name[i].visible = false;
Calling the list with changing the property of visible elements to the opposite (i.e. what was true will change to false, and what was false - to true):
list_name[i].visible != list_name[i].visible;
If, after all, it cannot be done in this particular way, is there another similar possibility?
As a general rule, often it is better to place a group of controls say inside of div, and then simple hide/show the div to show/hide the group of controls.
so say this:
<div id="BillAddress" runat="sever">
Text address, and more controls here
</div>
Then in code, you can hide/show the whole mess with
BillAddress.Style("display") = "none";
Or to show that group of controls, then this:
BillAddress.Style("display") = "normal";
So, web land, and web markup lends itself to MUCH better using span's, or div's, or whatever to group controls.
And the beauty of above, is then you can also often wirte client side code in JavaScript to hide/show groups of controls inside that div 100% with client side code.
Having stated + suggested the above?
You can also say cook up your "own" attributes on a group of controls.
Say:
<asp:TextBox ID="TextBox1" runat="server"
MyGroup="Billing" >
</asp:TextBox>
<asp:TextBox ID="txtNewCity" runat="server"
MyGroup="Billing>
</asp:TextBox>
So, note how in above I just made up a attribute for the control.
Then, in code, can do this:
For Each c As System.Web.UI.Control In Page.Controls
If c.Attributes("MyBilling") IsNot Nothing Then
// hide/show the control
So, in web land, I don't really think it makes a whole lot of sense to attempt to group some controls in a array - just drop all those controls inside of some div, and hide/show that div. But, you can use "tag" or even cook up + add your own attributes to controls, and then loop the controls in that page, or div or whatever.
For example, I cooked up my own "data binder" routine.
I simple will place a group of controls say inside of a "div" with a "id" and runat server.
Then, to load data into that "div" and set of controls?
I place controls in a div, and then I can do this:
int intPK = (int)ViewState[this.ID + "_MyPk"];
string strSQL = "SELECT * FROM " + this.MyTable + " WHERE ID = " + intPK;
DataTable rstData = General.MyRst(strSQL);
General.FLoader(this.EditRecord, rstData.Rows[0]);
In above, EditRecord is my "div"
The markup looks like:
<asp:TextBox ID="txtHotel" runat="server" f="HotelName" width="280"></asp:TextBox> <br />
<asp:TextBox ID="tFN" runat="server" f="FirstName" Width="140"></asp:TextBox> <br />
etc. etc.
So, I use a made up attribute called "f", where f="database column name"
So, with that simple idea, then I can load up a whole data form with about 3 lines of code.
So, say I click edit on a grid.
I pop this form:
but, the form data is done with my fLoader routine. All it does is look for "f" attributes, and fills out the control from the database.
And then for save, I have Fwriter. Does the same thing, but in reverse.
So, save button code for above is this:
protected void cmdSave_ServerClick(object sender, EventArgs e)
{
int intPK = (int)ViewState[this.ID + "_MyPk"];
string strSQL = "SELECT * FROM tblHotels WHERE ID = " + intPK;
DataTable rstData = General.MyRst(strSQL);
General.FWriterUpdate(this.EditRecord, rstData.Rows[0]);
}
So, Fwriter again just loops the controls inside of that div, and transfers back from the controls their values into the table.
So, in above, we see two examples of grouping controls, and then being able to "operate" on that group of controls.
No arrays required here. so, I used these concepts for my own data binding system, and thus I NEVER have to write code to load up each individual control from the database. Nor do I have to write code to send + save the data back to the database.
I means I quite much have ms-access like drag + drop of controls, and the shuffle from database to the form is done for me. And this all works due to the requiring to "group" and identify controls on the page, and what I want to do with that group of controls.
Edit: Processing conrols in an array or list
In all of the above "div" and control processing routines, we REALLY are doing the same as if we placed the controls into an array, or list.
For example, the floader routine does this: (we can pass it the current web page, or as more often a "div".
So, it looks like this:
foreach (System.Web.UI.Control c in F.Controls)
{
if (c.GetType() == typeof(TextBox))
{
TextBox ctlC = c as TextBox;
ctlC.Text = "zoo";
ctlC.Visible = true;
}
else if (c.GetType() == typeof(Label))
{
Label ctlC = c as Label;
}
else if (c.GetType() == typeof(DropDownList))
{
DropDownList ctlC = c as DropDownList;
}
else if (c.GetType() == typeof(CheckBox))
{
CheckBox ctlC = c as CheckBox;
}
I removed most of the code, but above shows how you can pass/have a bunch of controls in a page, or div or whatever.
So, my WHOLE post and narrative been based on the above approach - which I assumed was obvious here.
However, lets code up a collection, and thus make this even more obvious.
so this markup:
<asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
<br />
<asp:Label ID="Label1" runat="server" Text="Label"></asp:Label>
<br />
<asp:CheckBox ID="CheckBox2" runat="server" />
So, our code behind can then do this:
List<Control> mycontrols = new List<Control>();
mycontrols.Add(TextBox1);
mycontrols.Add(CheckBox2);
mycontrols.Add(Label1);
foreach (Control myC in mycontrols)
{
myC.Visible = false;
}
// set text value of controls
foreach (Control myC in mycontrols)
{
myC.Visible = false;
if (myC.GetType() == typeof(TextBox))
{
TextBox ctlC = myC as TextBox;
ctlC.Text = "zoo";
ctlC.Visible = true;
}
else if (myC.GetType() == typeof(Label))
{
Label ctlC = c as Label;
ctlC.Text = "zoo zoo";
}
else if (myC.GetType() == typeof(CheckBox))
{
CheckBox ctlC = c as CheckBox;
ctlC.Checked = true;
}
}
So, for visible, we can use visible property. but, for other features of the control, say like Text or whatever? We cast the control into its type, and thus can use say checked of the checkbox, and it does not even have a .text property.
Not sure if the title makes much sense, so here is the full context:
I'm coding in C#.
I've made an app with several UserControls, each one with many textboxes and radiobuttons.
All radiobuttons are placed in a panel in a set of 2, looking like this:
[ <label> O <radiobutton1text> O <radiobutton2text> ]
(while the first radiobutton have TabStop = true, and the second's TabStop = false)
When tabbing to such panel, only radiobutton1text is focused, and when hitting the LeftArrow key the radiobutton2text is selected. That's the desired outcome.
In order to make a UserControl load faster the second (and above) time, I'm not closing it but rather replacing it with a different UserControl each time the contents need to change.
But this rises an issue: When UserControl X is open, then on top of it I open UserControl Y and then back to X, the textboxes and radiobuttons still have the contents from the first session of when I had UserControl X open for the first time. (I need the contents of textboxes and radiobuttons to be reset after replacing a UserControl).
So I made a function that loops through all controls and empties their contents.
The problem is, when I uncheck the radiobuttons (and restore their TabStop state to true) in this function, the second radiobutton is tabbable after I check either one of them and then invoke the function, whereas it wasn't before going through this function.
The function:
public void BackToMain(object sender, EventArgs e)
{
// Go through all controls and empty each TextBox, RichTextBox, RadioButton or ComboBox.
int parentControlsCount = Controls.Count - 1;
for (int i = parentControlsCount; i >= 0; i--)
{
if (Controls[i].HasChildren == true)
{
int childrenControlsCount = Controls[i].Controls.Count - 1;
for (int j = childrenControlsCount; j >= 0; j--)
{
var controlType = Controls[i].Controls[j].GetType().ToString();
switch (controlType)
{
case "System.Windows.Forms.TextBox":
case "System.Windows.Forms.RichTextBox":
Controls[i].Controls[j].Text = null;
break;
case "System.Windows.Forms.RadioButton":
// Restore both properties to default value
((RadioButton)Controls[i].Controls[j]).Checked = false;
if (j == 1)
((RadioButton)Controls[i].Controls[j]).TabStop = true;
else if (j == 2)
((RadioButton)Controls[i].Controls[j]).TabStop = false;
break;
case "System.Windows.Forms.ComboBox":
((ComboBox)Controls[i].Controls[j]).SelectedIndex = -1;
break;
}
}
}
}
}
What am I doing wrong?
I ended up applying this gross hack- a function on every second radiobutton's CheckedChange:
private void DisableTabStopOnCheckedChange(object sender, EventArgs e)
{
// Assume the following STR:
// 1. In any radiobutton panel, select any radiobutton (without ever invoking BackToMain function in the first post);
// 2. Invoke the BackToMain function;
// 3. In the same radiobutton panel as in step #1, click the second radiobutton.
// Normally, without this function, if the user will now cycle through the controls using the Tab key, both the first and second radiobuttons will be tabbable,
// and that's because in the BackToMain function we reset their Checked and TabStop properies, and that's something that should be handled automatically by the control itself.
// Doing it manually means that for the *first time* selecting the second radiobutton, the first one's TabStop state won't update, which means both radiobuttons
// will have the TabStop state set to true, causing both to be tabbable.
// This is a gross hack to fix this by disabling TabStop on the first radio button if the second one is checked and the first one's TabStop state
// is true (this should happen only after BackToMain has been invoked).
if (((RadioButton)sender).Checked)
{
var firstRadioButton = ((RadioButton)sender).Parent.Controls[1];
if (((RadioButton)firstRadioButton).TabStop == true)
{
((RadioButton)firstRadioButton).TabStop = false;
}
}
}
Not a pretty solution, I know. But it works.
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.
hi I have a radio button list inside a repeater , the repeater is inside a Datalist.i need to get the value of the selected radio button. Also I need to select only a single radio in entire datalist using javascript.
You can do it with pure client side JavaScript regardless of Repeater, DataList or anything.
Have this code in your page:
<script type="text/javascript">
function GetSelectedRadioButtonValue(strGroupName) {
var arrInputs = document.getElementsByTagName("input");
for (var i = 0; i < arrInputs.length; i++) {
var oCurInput = arrInputs[i];
if (oCurInput.type == "radio" && oCurInput.name == strGroupName && oCurInput.checked)
return oCurInput.value;
}
return "";
}
</script>
Then to get the selected value call the function passing the name of the radio buttons group - all radio buttons with same name considered a group and the browser will let the user select only one of these.
Live test case: http://jsfiddle.net/yahavbr/BL9xJ/
I would use the normal HTML Radio Button control. Everything else is pretty complicated.
Then you can use the following code to figure out which one is selected:
http://remy.supertext.ch/2008/02/find-checked-radio-button-in-aspnet/
I'm using C# in VS2005. For my application I need to create four radio buttons. My form looks like:
A(Radio Button)
B(Radio Button)
C(Radio Button)
D(Radio Button)
Submit (Button)
When a user clicks the submit button I need to know which radio button is checked. How can I determine this?
I would add all the radio buttons to a List<RadioButton> which would help you innumerate through them when the submit is checked to figure out which one is checked.
You can use the Checked Property of a RadioButton to see if it is checked:
bool isChecked = radA.Checked;
I often use the following helper function to get exactly the RadioButton which is checked:
public RadioButton GetCheckedRadioButton(Control container)
{
if (container == null) {
return null;
}
else if (container is RadioButton) {
return GetCheckedRadioButton(container.Parent);
}
else {
foreach (Control childControl in container.Controls) {
if (childControl is RadioButton) {
RadioButton radioBtn = (RadioButton) childControl;
if (radioBtn.Checked) {
return radioBtn;
}
}
}
return null;
}
}
Then, you can simply call this function using one of your controls or it's container, and do a switch statement, as such:
switch(GetCheckedRadioButton(radA)) {
case radA:
// radA is checked
break;
case radB:
// radB is checked
break;
}
Personally, I find it less verbose than the usual:
if(radA.Checked) {
//radA is checked
}
else if(radB.Checked) {
//radB is checked
}
If you know for sure that you will only need 4 RadioButtons, then I'd just write code similar to this.
if (Radio1.Checked) ...
if (Radio2.Checked) ...
if (Radio3.Checked) ...
...
If you know that only one of them can be checked at the same time (using a group box or some other mechanism) then you can optimise this by using "else if" instead.
However if there is a possibility that you will need more, this can get wasteful, so I agree with other answers, you should put them in a collection of your choice and use it to loop through them, to see which ones are checked.