How to trigger event when clicking on a selected tab page header of a tab control - c#

I am doing a Winform application in C# and I have some tab pages, say tabPage1, tabPage2 and tabPage3, in a tab control, and tabPage1 is selected.
I want to trigger event when any tab page header is clicked, but I could do it only for page change (by using SelectedIndexChanged) but not click on a selected tab page header.
I tried with Selecting and Selected events but both of them didn't not work. I searched on MSDN but didn't find any Click event defined on a page header. So how should I achieve this?
One further question, is it possible, and how, to detect DoubleClick on a selected tab page?

Just use the tabcontrol's MouseDoubleClick event. You'll have to iterate the tabs to find out what specific tab was clicked:
private void tabControl1_MouseDoubleClick(object sender, MouseEventArgs e) {
for (int ix = 0; ix < tabControl1.TabCount; ++ix) {
if (tabControl1.GetTabRect(ix).Contains(e.Location)) {
// Found it, do something
//...
break;
}
}
}
Do keep in mind that this is completely undiscoverable to the user, he'll never think to double-click the tab. You'll have to write a manual.

You should be doing your stuff on
TabIndexChanged
If you want to load the contents on your 3rd tab, for example, handle the TabIndexChanged on your tab control, do a switch for each tabPage.Index and then do whatever is needed when user clicks on that tab.

private void tabPage1_Layout(object sender, LayoutEventArgs e)
{
//do something
}

Related

Tab index is not working on radio buttons

This is the part of my form that I am asking about
This is the tab index:
The problem that the tab goes from Farmer Audi Status to Yes, then to Ownder Bank Name instead of going to No
please notice that the yes and no already have 0.1.6.0 and 0.1.6.1 respectively.
could you help me please?
Notice
both radio buttons has TabStop property to True
From How to: Set the Tab Order on Windows Forms (MSDN):
A radio button group has a single tab stop at run time. The selected button (that is, the button with its Checked property set to true) has its TabStop property automatically set to true, while the other buttons have their TabStop property set to false.
In other words, what you're seeing is normal. Those "Yes/No" radio buttons are in the same group, and you can't tab between radio buttons in the same group. As you tab, you'll only focus on the currently selected one, then move to the next control on the form (in your case, a TextBox).
To work around this, you could place each radio button in its own container (such as a Panel), which means you'd have two "groups" each with one radio button. But then you lose the built-in functionality that automatically deselects one radio button when you select the other. Your user will be able to select both radio buttons, so you'd need to add some logic that disables the other. If you decide to try that, experiment with the radio buttons' CheckedChanged or Click / MouseClick events.
As Steve said, and as stated in the answer he linked to, the way it works out-of-the-box is expected behavior for Windows, so think twice before overriding it unless you have a good reason for doing so.
It worked for me!
first you have to create a method like this:
private void TabStopChanged(object sender, EventArgs e)
{
((RadioButton)sender).TabStop = true;
}
and then, put this in your Form_Load event:
private void Form_Load(object sender, EventArgs e)
{
foreach (var item in this.Controls)
{
if (item.GetType() == typeof(RadioButton))
((RadioButton)item).TabStopChanged += new System.EventHandler(TabStopChanged);
}
}
For radio buttons, you don't have to use Tab to navigate. Just use right and left keys to traverse radio buttons.
Check out this link to read more - https://www.csun.edu/universal-design-center/web-accessibility-criteria-tab-order

Adding close button on tab header in c# winforms [duplicate]

My scenario is the following:
I am working on a winforms application in C# that has a button inside the main page of a tabcontrol that will generate another tabpage each time that it is clicked. Each new tabpage will contain a layout defined by a user control.
My Questions are:
How can I allow the user to then close one of the tabs that were created dynamically at runtime?
How might I go about modifying the tabcontrol itself so that it has a small 'X' in each tab that the user may click on in order to close that particular tab? (Like Firefox has)
How can I expose the SelectedIndex property of the tabcontrol to the user control if I want to close the tab with a button inside the user control instead?
I found this code and was very helpful to me:
private void tabControl_MouseUp(object sender, MouseEventArgs e)
{
// check if the right mouse button was pressed
if(e.Button == MouseButtons.Right)
{
// iterate through all the tab pages
for(int i = 0; i < tabControl1.TabCount; i++)
{
// get their rectangle area and check if it contains the mouse cursor
Rectangle r = tabControl1.GetTabRect(i);
if (r.Contains(e.Location))
{
// show the context menu here
System.Diagnostics.Debug.WriteLine("TabPressed: " + i);
}
}
}
}
TabControl: How To Capture Mouse Right-Click On Tab
I created a derived tab control about one year ago. I am not going to post the source here, because it's about 700 lines long and coded quite messy. Maybe I will find some time to clean the code up and then release it here. For now I will briefly outline the way it is build.
Each tab page has a 'X' icon to the left of the title and the tab pages support reordering by drag and drop and moving them between multiple tab control.
I choose the easy way to get the icon on the tab pages. The tab control has the TabControl.ImageList property and a tab page has a TabPage.ImageIndex property. So I just added three icons to a image list - normal, hover, pressed - and process the mouse events.
With TabControl.GetTabRect() you can test if the mouse is over a specific tab pages and with some math you find if it is over the icon. Then you just need to change the icon depending on the mouse button state and eventually remove the tab page under the mouse if the button was pressed.
The main problem with this solution is, that calculating if the mouse is over the icon requires to know where the icon is painted relative to the tab page and this might change with a new windows version. And the icon is to the left of the title, but that does not look too bad.
I did the following:
on the create (add) TabPage stage, I added a toolStrip
ToolStrip ts = new ToolStrip();
ts.Dock = DockStyle.Top;
ts.RightToLeft = System.Windows.Forms.RightToLeft.Yes;
Then, create the X button and add it to toolstrip
ToolStripButton ToolStripButton = new ToolStripButton("X");
ts.Items.Add(ToolStripButton);
create an event on clicking the X button
ToolStripButton.Click += new EventHandler(ToolStripButton_Click);
add toolstrip to the tabpage
tabControl1.TabPages[curenttabpage].Controls.Add(ts);
now for the ToolStripButton_Click is as follows:
void ToolStripButton_Click(object sender, EventArgs e)
{
ToolStripButton t = (ToolStripButton)(sender);
ToolStrip ts = t.Owner;
TabPage tb = (TabPage)
(ts.Parent);tabControl1.TabPages.Remove(tb);
}
Maybe it is not as you want, but it will work well.
I created a setup that is similar.
Each control that is added to the tab page at runtime is derived from a special base control I created. This base control has a close button (along with some other features such as safe to close flag).
Close tab code I'm using on my base control:
TabPage tabpage = (TabPage)this.Parent;
TabControl tabControl = (TabControl)tabpage.Parent;
tabControl.TabPages.Remove(parent);
I know this is an old thread but I did find this link that will allow you to "hide" tabs in an array and then you can just re-load the tabs you want at run time. I added this more for a place I can easily find it again.
This code might help throgh closing the tab controls with middle mouse click :
private void tabControl1_MouseDown(object sender, MouseEventArgs e)
{
if (e.Button != System.Windows.Forms.MouseButtons.Middle)
return;
for (int i = 0; i < MainTabControl.TabPages.Count; i++)
{
if (this.MainTabControl.GetTabRect(i).Contains(e.Location))
{
this.MainTabControl.TabPages.RemoveAt(i);
return;
}
}
}
It´s works!
TabPage tabpage = (TabPage)this.Parent;
TabControl tabControl = (TabControl)tabpage.Parent;
tabControl.TabPages.Remove(tabpage);

TabControl Cancel change of tabs

I am using TabControl_SelectedIndexChanged event when the user change tabs. The TabControl.SelectedIndex / TabControl.SelectedTab return only the new tab. Is there any way I can get the previous tab? Or must I stick with the obvious store the current tab every time I change tabs?
I want to use this to cancel a change of tabs under certain conditions, like there is unsaved changes.
If you want to cancel the change of a tab, you can use the Deselecting event. There you can cancel the change by setting property Cancel of the provided TabControlCancelEventArgs to true.
Check out http://msdn.microsoft.com/en-us/library/system.windows.forms.tabcontrol.selected%28v=vs.80%29.aspx
There are events better suited for what you want to do.
I used tabControl Selected method to prevent users selecting a certain tab, in other word, to disable a tab page.
TabPage currentPage;
private void tabControl1_Selected(object sender, TabControlEventArgs e)
{
if (e.TabPage == tabNotAllowed)
{
tabControl1.SelectedTab = currentPage;
MessageBox.Show("You cannot use the tab you selected.");
}
else
{
currentPage = e.TabPage;
}
}

Detect if mouse click hits a item not in listbox [C#]

If the user click on a item in the listbox, the listboxItems_SelectedIndexChanged is called. But, even if the user miss an item and randomly clicks inside the listbox (not on items) the listboxItems_SelectedIndexChanged is still called.
How can I change this? I only want action on item click.
Note: removing the ability to navigate the application with keyboard is not a option.
I guess that in some cases you don't have enough list items in your control, therefore you have some space that you can click on and then SelectedIndexChanged is fired.
I guess you cannot dynamically resize the control to always fit the number of list items or else you wouldn't be asking this question.
Now, what should happen when the user click (selects) the same list item? Should some logic happen even though the selected index is the same (so when it was clicked the first time the same logic happend)?
If you require that selecting the same index more than once should be ignored then you could use the following hack:
Keep a variable at the form scope (the form containing the listbox control) and each time the selection index changes set that variable. Then use it later to check if the same selection has been made to ignore handling the event. Here is an example:
private int _currSelIdx = -1; // Default value for the selected index when no selection
private void listBox1_SelectedIndexChanged(object sender, EventArgs e)
{
if (listBox1.SelectedIndex == _currSelIdx)
return;
Console.WriteLine(listBox1.SelectedIndex);
_currSelIdx = listBox1.SelectedIndex;
}
It ain't pretty, but hey...whatever works!
Maybe SelectedIndexChanged is not the right place to put your logic, since it is triggered even when you change the selection with the keyboard.
I would use MouseClick instead, checking if the click occurred over the selected item, i.e. something like this:
private void listBox1_MouseClick(object sender, MouseEventArgs e)
{
if (listBox1.SelectedIndex < 0 || !listBox1.GetItemRectangle(listBox1.SelectedIndex).Contains(e.Location))
MessageBox.Show("no click");
else
MessageBox.Show("click on item " + listBox1.SelectedIndex.ToString());
}
This link may help, instead of double click, implement the same for single click
i want to detect an item double click in a winforms listbox control. [how to handle click on blank area?]

Focusing WebBrowser control in a C# application

I have a WebBrowser control hosted in a windows Form. The control is used to display hyperlinks which get created at runtime. These links point to some HTML pages and PDF documents.
The problem is that when the form hosting the browser control is loaded, the focus is on the form. When the TAB key is pressed, the focus does not shift to the first hyperlink. However, if I perform a mouse click on the control and then hit the TAB key, the tab focus is now on the first hyper link. I tried using Select() on the WebBrowser control and then I called Focus(), but it doesn't solve the problem.
Any ideas on how to set the tab focus on the first hyperlink at load? Thanks.
Cheers,
Harish
I guess it might be because the focus is set before the page is fully loaded. Try this:
private void Go(string url)
{
webBrowser1.Navigate(url);
webBrowser1.DocumentCompleted += new WebBrowserDocumentCompletedEventHandler(webBrowser1_DocumentCompleted);
}
void webBrowser1_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
{
webBrowser1.Document.Body.Focus();
}
You could also automatically select the focus on the first link directly by getting the HtmlElement of that first link.
If the above doesn't work, you might want to check other parts of your code to see if anything else is capturing the focus. Try searching for Select, Focus and ActiveControl in your code.
Use form.ShowDialog(form) instead on form.Show(), then it will work !
where form is the running instance of your windows Form
This is my solution
private void txtAdres_KeyPress(object sender, KeyPressEventArgs e)
{
int licznik = 1;
if (e.KeyChar == (char)13)
{
string adres = txtAdres.Text;
webBrowser1.Navigate(adres);
licznik = 0;
}
if (licznik == 0)
{
webBrowser1.Focus();
}
}
In a normal scenario it should be sufficient for you to set the TabIndex of the WebBrowser control to zero. This way, when the form loads the control will be focused and pressing TAB will iterate through the links.
Note that you should also change the TabIndex of the other controls on the form.
If this does not solve your problem, you need to add more detail on the complexity of the form hosting the control.

Categories

Resources