Hello,
I am tasked to replicate the New Tab functionality of Google Chrome. I have attached sample code below that mostly accomplishes this. However there is still one bug that I am unable to fix, and it is related to the RadDock tabstrip not redrawing after ActivateWindow() is called.
To reproduce this problem, please run the following code. You should see a tab named "New Tab 0" and a mini-tab to its right, which will create additional new tabs if you click on it. Click the mini-tab so you have two named tabs. Then, right-click on the right-most named tab ("New Tab 1", unless you created more) and select "Floating" to pop it out. Here is where the problem happens. We never want the MiniTab to have focus, so the method MiniTabGotFocus() will have been called, which activates the window to its left. However, the tabs are not redrawn to reflect this. BUT, if you click on Form1 parent dialog to give it focus (or close that popped out window), the tabs will immediately redraw correctly. So the window to the left was in fact Activated, but the tabs do not reflect this until Form1 has focus again.
Does this make sense? I have tried to Invalidate() the TabStrip but that does not force it to redraw. I can only cause it to redraw correctly by clicking on the Form1 parent dialog to give it focus. What I would like help on is how to force the TabStrip to redraw.
This is using Telerik v2011-8-31.
Thanks,
Michelle
I am tasked to replicate the New Tab functionality of Google Chrome. I have attached sample code below that mostly accomplishes this. However there is still one bug that I am unable to fix, and it is related to the RadDock tabstrip not redrawing after ActivateWindow() is called.
To reproduce this problem, please run the following code. You should see a tab named "New Tab 0" and a mini-tab to its right, which will create additional new tabs if you click on it. Click the mini-tab so you have two named tabs. Then, right-click on the right-most named tab ("New Tab 1", unless you created more) and select "Floating" to pop it out. Here is where the problem happens. We never want the MiniTab to have focus, so the method MiniTabGotFocus() will have been called, which activates the window to its left. However, the tabs are not redrawn to reflect this. BUT, if you click on Form1 parent dialog to give it focus (or close that popped out window), the tabs will immediately redraw correctly. So the window to the left was in fact Activated, but the tabs do not reflect this until Form1 has focus again.
Does this make sense? I have tried to Invalidate() the TabStrip but that does not force it to redraw. I can only cause it to redraw correctly by clicking on the Form1 parent dialog to give it focus. What I would like help on is how to force the TabStrip to redraw.
This is using Telerik v2011-8-31.
Thanks,
Michelle
using
System;
using
System.Drawing;
using
System.Linq;
using
System.Windows.Forms;
using
Telerik.WinControls.UI.Docking;
namespace
WindowsFormsApplication1
{
public
class
Form1 : Form
{
#region Windows Form Designer generated code
/// <summary>
/// Required designer variable.
/// </summary>
private
System.ComponentModel.IContainer components;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected
override
void
Dispose(
bool
disposing)
{
if
(disposing && (components !=
null
))
{
components.Dispose();
}
base
.Dispose(disposing);
}
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private
void
InitializeComponent()
{
this
.chartingDock =
new
Telerik.WinControls.UI.Docking.RadDock();
((System.ComponentModel.ISupportInitialize)(
this
.chartingDock)).BeginInit();
this
.chartingDock.SuspendLayout();
this
.SuspendLayout();
//
// chartingDock
//
this
.chartingDock.Dock = System.Windows.Forms.DockStyle.Fill;
this
.chartingDock.Location =
new
System.Drawing.Point(0, 0);
this
.chartingDock.Name =
"chartingDock"
;
this
.chartingDock.Padding =
new
System.Windows.Forms.Padding(5);
this
.chartingDock.RootElement.MinSize =
new
System.Drawing.Size(25, 25);
this
.chartingDock.RootElement.Padding =
new
System.Windows.Forms.Padding(5);
this
.chartingDock.Size =
new
System.Drawing.Size(573, 397);
this
.chartingDock.SplitterWidth = 4;
this
.chartingDock.TabIndex = 0;
this
.chartingDock.TabStop =
false
;
this
.chartingDock.Text =
"chartingDock"
;
//
// Form1
//
this
.AutoScaleDimensions =
new
System.Drawing.SizeF(6F, 13F);
this
.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this
.ClientSize =
new
System.Drawing.Size(573, 397);
this
.Controls.Add(
this
.chartingDock);
this
.IsMdiContainer =
true
;
this
.Name =
"Form1"
;
this
.Text =
"Form1"
;
((System.ComponentModel.ISupportInitialize)(
this
.chartingDock)).EndInit();
this
.chartingDock.ResumeLayout(
false
);
this
.ResumeLayout(
false
);
}
#endregion
private
RadDock chartingDock;
public
Form1()
{
InitializeComponent();
chartingDock.AutoDetectMdiChildren =
true
;
chartingDock.DockWindowClosed += ChartingDockDockWindowClosed;
chartingDock.DockWindowClosing += ChartingDockDockWindowClosing;
chartingDock.TransactionCommitted += ChartingDockTransactionCommitted;
chartingDock.DockWindowAdded += ChartingDockDockWindowAdded;
chartingDock.GetDefaultDocumentTabStrip(
true
).TabStripElement.ItemsChanged += TabStripElement_ItemsChanged;
EnsureNewChartMiniTabExists();
}
private
int
count;
private
void
AddTab()
{
AddTab(
"New Tab "
+ count++);
}
private
void
AddTab(
string
title)
{
var f =
new
ToolWindow
{
Text = title,
};
if
(title == NewChartTabText) f.BackColor = Color.Black;
chartingDock.SetWindowState(f, DockState.TabbedDocument);
}
private
const
string
NewChartTabText =
" "
;
private
DockWindow switchTab;
void
ChartingDockDockWindowClosing(
object
sender, DockWindowCancelEventArgs e)
{
var index = Array.IndexOf(chartingDock.DocumentManager.DocumentArray, e.NewWindow);
switchTab = index == chartingDock.DocumentManager.DocumentArray.Count() - 2 && index > 0
? chartingDock.DocumentManager.DocumentArray[index - 1]
:
null
;
}
void
ChartingDockDockWindowClosed(
object
sender, DockWindowEventArgs e)
{
if
(switchTab !=
null
) chartingDock.ActivateWindow(switchTab);
}
void
ChartingDockTransactionCommitted(
object
sender, RadDockTransactionEventArgs e)
{
EnsureNewChartMiniTabExists();
//for when the only chart is double-clicked to pop out, create a new blank chart
if
(chartingDock.DocumentManager.DocumentArray.Where(w => w.Text != NewChartTabText).Count() == 0)
{
AddTab();
}
//if the committed window was the newcharttab, subscribe to the click event
var window = e.Transaction.AssociatedWindows.FirstOrDefault();
if
(window !=
null
&& window.Text == NewChartTabText)
{
window.TabStripItem.Click -= MiniTabClicked;
window.TabStripItem.Click += MiniTabClicked;
window.GotFocus += MiniTabGotFocus;
}
}
private
void
EnsureNewChartMiniTabExists()
{
if
(chartingDock.DocumentManager.DocumentArray.Where(w => w.Text == NewChartTabText).Count() == 0)
{
AddTab(NewChartTabText);
}
}
static
void
ChartingDockDockWindowAdded(
object
sender, DockWindowEventArgs e)
{
var window = e.DockWindow
as
ToolWindow;
if
(window ==
null
)
return
;
DockTabStrip strip = e.DockWindow.DockTabStrip;
if
(strip !=
null
)
{
var count = strip.Controls.Count;
var index = e.DockWindow.Text == NewChartTabText ? count - 1 : count - 2;
if
(index < 0) index = 0;
strip.Controls.SetChildIndex(e.DockWindow, index);
}
}
void
TabStripElement_ItemsChanged(
object
sender, Telerik.WinControls.UI.RadPageViewItemsChangedEventArgs e)
{
var window = chartingDock.DocumentManager.DocumentArray.Where(w => w.Text == NewChartTabText).FirstOrDefault()
as
ToolWindow;
if
(window ==
null
)
return
;
var tabCount = chartingDock.DocumentManager.DocumentArray.Count();
var index = Array.IndexOf(chartingDock.DocumentManager.DocumentArray, window);
if
(index >= tabCount - 1)
return
;
DockTabStrip strip = window.DockTabStrip;
if
(strip ==
null
)
return
;
strip.Controls.SetChildIndex(window, tabCount - 1);
}
private
void
MiniTabClicked(
object
sender, EventArgs e)
{
AddTab();
}
private
void
MiniTabGotFocus(
object
sender, EventArgs e)
{
var tabCount = chartingDock.DocumentManager.DocumentArray.Count();
if
(tabCount < 2)
return
;
var window = chartingDock.DocumentManager.DocumentArray[tabCount - 2];
chartingDock.ActivateWindow(window);
}
}
}