Contrôle des onglets verticaux avec texte horizontal dans Winforms
j'aimerais que les onglets de mon TabControl s'affichent à gauche, ou parfois à droite.
À la différence du Système.Windows.Forme.TabControl, cependant, je voudrais que le texte reste horizontal au lieu d'être tourné de 90 ou 270 degrés à l'horizontale.
Voici quelques photos illustrant le concept
bien que je puisse écrire le code pour le faire moi-même dans environ une heure ou deux, je juste j'ai pensé demander d'abord s'il est existant Winforms contrôle qui implémente cette fonctionnalité.
NB: toute solution existante devrait de préférence être non commerciale.
Merci.
4 réponses
Je ne sais pas à quel point c'est robuste et je ne peux pas prétendre l'avoir créé mais... http://www.dreamincode.net/forums/topic/125792-how-to-make-vertical-tabs/
Voici une façon de le faire.
donc d'abord nous allons changer son alignement à gauche, en définissant la propriété:
Alignement = Gauche
si vous avez des thèmes XP activés, alors vous pouvez remarquer la mise en page bizarre du contrôle des onglets. Ne vous inquiétez pas, nous allons faire fin.
comme vous avez peut-être remarqué que les onglets sont verticaux, et que notre exigence est horizontale. Donc on peut changer la taille des onglets. Mais avant de faire cela, nous devons définir la propriété SizeMode comme,
SizeMode = Fixed
maintenant nous pouvons changer la taille en utilisant la propriété ItemSize,
ItemSize = 30, 120 Largeur = 30 et Hauteur = 120
après avoir réglé L'alignement = Left, Tab control tourne le Les onglets qui provoquent la largeur et la hauteur semblent être inversés. C'est pourquoi, lorsque nous augmenter la Hauteur, nous voyons que la largeur augmente et lorsque l'on augmente la largeur, la hauteur est effectué.
maintenant le texte sera aussi affiché, mais verticalement. Malheureusement, il n'existe pas de solution simple à ce problème. Pour cela, nous devons écrire le texte nous-mêmes. Pour ce faire, nous allons d'abord définir le mode de dessin
DrawMode = Owndrawfixed
01
Private Sub TabControl1_DrawItem(ByVal sender As Object, ByVal e As System.Windows.Forms.DrawItemEventArgs) Handles TabControl1.DrawItem
Dim g As Graphics
Dim sText As String
Dim iX As Integer
Dim iY As Integer
Dim sizeText As SizeF
Dim ctlTab As TabControl
ctlTab = CType(sender, TabControl)
g = e.Graphics
sText = ctlTab.TabPages(e.Index).Text
sizeText = g.MeasureString(sText, ctlTab.Font)
iX = e.Bounds.Left + 6
iY = e.Bounds.Top + (e.Bounds.Height - sizeText.Height) / 2
g.DrawString(sText, ctlTab.Font, Brushes.Black, iX, iY)
End Sub
j'ai décidé de partager le code que j'ai développé depuis certaines personnes, telles que Amit Andharia qui voudraient en bénéficier.
C'est le résultat après que j'ai implémenté réponse de Rob P..
Notes:
- Plein moment de la conception de soutien
- redimensionnement Automatique des onglets (jusqu'à 128px de large)
- Onglet icônes mise en œuvre
- les propriétés non utilisées ont été cachées
le code peut être téléchargé à partir de ici.
C'est le code d'un contrôle d'onglet personnalisé que j'aime beaucoup. Vous devrez copier et coller ce code dans une nouvelle classe puis reconstruire le projet. Vous verrez un nouveau contrôle d'utilisateur personnalisé s'afficher dans votre boîte à outils.
Imports System.Drawing.Drawing2D
Class DotNetBarTabcontrol
Inherits TabControl
Sub New()
SetStyle(ControlStyles.AllPaintingInWmPaint Or ControlStyles.ResizeRedraw Or ControlStyles.UserPaint Or ControlStyles.DoubleBuffer, True)
DoubleBuffered = True
SizeMode = TabSizeMode.Fixed
ItemSize = New Size(44, 136)
End Sub
Protected Overrides Sub CreateHandle()
MyBase.CreateHandle()
Alignment = TabAlignment.Left
End Sub
Function ToPen(ByVal color As Color) As Pen
Return New Pen(color)
End Function
Function ToBrush(ByVal color As Color) As Brush
Return New SolidBrush(color)
End Function
Protected Overrides Sub OnPaint(ByVal e As PaintEventArgs)
Dim B As New Bitmap(Width, Height)
Dim G As Graphics = Graphics.FromImage(B)
Try : SelectedTab.BackColor = Color.White : Catch : End Try
G.Clear(Color.White)
G.FillRectangle(New SolidBrush(Color.FromArgb(246, 248, 252)), New Rectangle(0, 0, ItemSize.Height + 4, Height))
'G.DrawLine(New Pen(Color.FromArgb(170, 187, 204)), New Point(Width - 1, 0), New Point(Width - 1, Height - 1)) 'comment out to get rid of the borders
'G.DrawLine(New Pen(Color.FromArgb(170, 187, 204)), New Point(ItemSize.Height + 1, 0), New Point(Width - 1, 0)) 'comment out to get rid of the borders
'G.DrawLine(New Pen(Color.FromArgb(170, 187, 204)), New Point(ItemSize.Height + 3, Height - 1), New Point(Width - 1, Height - 1)) 'comment out to get rid of the borders
G.DrawLine(New Pen(Color.FromArgb(170, 187, 204)), New Point(ItemSize.Height + 3, 0), New Point(ItemSize.Height + 3, 999))
For i = 0 To TabCount - 1
If i = SelectedIndex Then
Dim x2 As Rectangle = New Rectangle(New Point(GetTabRect(i).Location.X - 2, GetTabRect(i).Location.Y - 2), New Size(GetTabRect(i).Width + 3, GetTabRect(i).Height - 1))
Dim myBlend As New ColorBlend()
myBlend.Colors = {Color.FromArgb(232, 232, 240), Color.FromArgb(232, 232, 240), Color.FromArgb(232, 232, 240)}
myBlend.Positions = {0.0F, 0.5F, 1.0F}
Dim lgBrush As New LinearGradientBrush(x2, Color.Black, Color.Black, 90.0F)
lgBrush.InterpolationColors = myBlend
G.FillRectangle(lgBrush, x2)
G.DrawRectangle(New Pen(Color.FromArgb(170, 187, 204)), x2)
G.SmoothingMode = SmoothingMode.HighQuality
Dim p() As Point = {New Point(ItemSize.Height - 3, GetTabRect(i).Location.Y + 20), New Point(ItemSize.Height + 4, GetTabRect(i).Location.Y + 14), New Point(ItemSize.Height + 4, GetTabRect(i).Location.Y + 27)}
G.FillPolygon(Brushes.White, p)
G.DrawPolygon(New Pen(Color.FromArgb(170, 187, 204)), p)
If ImageList IsNot Nothing Then
Try
If ImageList.Images(TabPages(i).ImageIndex) IsNot Nothing Then
G.DrawImage(ImageList.Images(TabPages(i).ImageIndex), New Point(x2.Location.X + 8, x2.Location.Y + 6))
G.DrawString(" " & TabPages(i).Text, Font, Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
Else
G.DrawString(TabPages(i).Text, New Font(Font.FontFamily, Font.Size, FontStyle.Bold), Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
End If
Catch ex As Exception
G.DrawString(TabPages(i).Text, New Font(Font.FontFamily, Font.Size, FontStyle.Bold), Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
End Try
Else
G.DrawString(TabPages(i).Text, New Font(Font.FontFamily, Font.Size, FontStyle.Bold), Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
End If
G.DrawLine(New Pen(Color.FromArgb(200, 200, 250)), New Point(x2.Location.X - 1, x2.Location.Y - 1), New Point(x2.Location.X, x2.Location.Y))
G.DrawLine(New Pen(Color.FromArgb(200, 200, 250)), New Point(x2.Location.X - 1, x2.Bottom - 1), New Point(x2.Location.X, x2.Bottom))
Else
Dim x2 As Rectangle = New Rectangle(New Point(GetTabRect(i).Location.X - 2, GetTabRect(i).Location.Y - 2), New Size(GetTabRect(i).Width + 3, GetTabRect(i).Height + 1))
G.FillRectangle(New SolidBrush(Color.FromArgb(246, 248, 252)), x2)
G.DrawLine(New Pen(Color.FromArgb(170, 187, 204)), New Point(x2.Right, x2.Top), New Point(x2.Right, x2.Bottom))
If ImageList IsNot Nothing Then
Try
If ImageList.Images(TabPages(i).ImageIndex) IsNot Nothing Then
G.DrawImage(ImageList.Images(TabPages(i).ImageIndex), New Point(x2.Location.X + 8, x2.Location.Y + 6))
G.DrawString(" " & TabPages(i).Text, Font, Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
Else
G.DrawString(TabPages(i).Text, Font, Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
End If
Catch ex As Exception
G.DrawString(TabPages(i).Text, Font, Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
End Try
Else
G.DrawString(TabPages(i).Text, Font, Brushes.DimGray, x2, New StringFormat With {.LineAlignment = StringAlignment.Center, .Alignment = StringAlignment.Center})
End If
End If
Next
e.Graphics.DrawImage(B.Clone, 0, 0)
G.Dispose() : B.Dispose()
End Sub
End Class
il y a un tutoriel fourni par Microsoft pour le faire avec le TabControl existant sur MSDN, avec un exemple de code donné à la fois en C# et Visual Basic .NET. Leur méthode est basée sur l'utilisation du dessin du propriétaire. Résumant leurs étapes ci-dessous:
définir les Alignement propriété Droit.
assurez-vous que tous les onglets ont la même largeur horizontale en réglant le SizeMode propriété Fixe.
mettez le ItemSize bien à votre taille préférée pour les onglets, en gardant à l'esprit que la largeur et la hauteur sont inversés.
mettez le DrawMode propriété OwnerDrawFixed.
configurer un gestionnaire d'événements pour lesDrawItem événement, et le lieu de votre propriétaire de dessin code n' dictant comment chaque onglet doit être affiché. Leur exemple de code C# pour le gestionnaire d'événements est reproduit ci-dessous pour plus de commodité (il suppose que votre TabControl est nommé
tabControl1
:private void tabControl1_DrawItem(Object sender, System.Windows.Forms.DrawItemEventArgs e) { Graphics g = e.Graphics; Brush _textBrush; // Get the item from the collection. TabPage _tabPage = tabControl1.TabPages[e.Index]; // Get the real bounds for the tab rectangle. Rectangle _tabBounds = tabControl1.GetTabRect(e.Index); if (e.State == DrawItemState.Selected) { // Draw a different background color, and don't paint a focus rectangle. _textBrush = new SolidBrush(Color.Red); g.FillRectangle(Brushes.Gray, e.Bounds); } else { _textBrush = new System.Drawing.SolidBrush(e.ForeColor); e.DrawBackground(); } // Use our own font. Font _tabFont = new Font("Arial", (float)10.0, FontStyle.Bold, GraphicsUnit.Pixel); // Draw string. Center the text. StringFormat _stringFlags = new StringFormat(); _stringFlags.Alignment = StringAlignment.Center; _stringFlags.LineAlignment = StringAlignment.Center; g.DrawString(_tabPage.Text, _tabFont, _textBrush, _tabBounds, new StringFormat(_stringFlags)); }
Vous pouvez probablement expérimenter avec votre ItemSize
propriété et le _tabFont
valeur à partir du code ci-dessus pour affiner l'apparence de vos onglets à tout ce dont vous avez besoin. Pour un style encore plus fantaisiste, je recommande de regarder cet autre article MSDN départ point.
(Source: Comment: afficher des onglets alignés latéralement avec TabControl (MSDN))