WPF adaptive can close TabControl browser-like tabs

Source: Internet
Author: User

Effect:

Although it is adaptive can be closed TabControl, but TabControl do not need to change, rather called adaptive can be closed tabitem.

General idea: Build a user control, inherit from TabItem, inside Put a button, click the time in the TabControl to remove itself. When adding, removing TabItem and TabControl dimension changes, the appropriate width is calculated by the number of items.

New User Control

Creates a new user control and inherits from TabItem so that it has all the properties and events of TabItem. This feature does not require custom dependency properties and events. It is used exactly like TabItem.

After the construction, replace the UserControl with TabItem and remove the superfluous parts.

Background inheritance from UserControl to inherit from TabItem

Change Style Add Close button

Add a favorite style to the Xmal, the main thing is to add a button in the template, register a click event, to close.

 1 <style targettype= "{x:type TabItem}" > 2 <setter property= "BorderBrush" value= "Black" ></sette R> 3 <setter property= "Background" value= "White" ></Setter> 4 <setter property= "F  Oreground "value=" Black "></Setter> 5 <setter property=" Padding "value=" 5,0,0,0 "></Setter> 6 <setter property= "HorizontalAlignment" value= "left" ></Setter> 7 <setter Property = "VerticalAlignment" value= "Center" ></Setter> 8 <setter property= "Horizontalcontentalignment" Valu E= "left" ></Setter> 9 <setter property= "verticalcontentalignment" value= "Center" ></Setter> Ten <setter property= "Template" >11 <setter.value>12 <control Template targettype= "{x:type TabItem}" >13 <border cornerradius= "5,0,0,0" borderbrush= "{Templ Atebinding BorderBrush} " borderthickness= "{TemplateBinding borderthickness}" background= "{TemplateBinding Background}" >14                                     <grid>15 <grid.columndefinitions>16 <columndefinition width= "*" ></columndefinition>17 <columndefinition Wi                                 Dth= "></columndefinition>18 </grid.columndefinitions>19" <contentpresenter grid.column= "0" contentsource= "Header" margin= "{TemplateBinding Padding}" Horizontala Lignment= "{TemplateBinding horizontalcontentalignment}" verticalalignment= "{TemplateBinding Verticalcontentalignment} "></contentpresenter>20 <button grid.column=" 1 "Name=                         "Btn_close" click= "Btn_close_click" ></button>21 </grid>22 </border>23 <controltemplate.triggers>24 <trigger property= "IsSelected" value= "true" >25 <setter property= "Background" value= "#FFFF923E" ></setter>26 & Lt                         Setter property= "Foreground" value= "white" ></setter>27 </trigger>28 </controltemplate.triggers>29 </controltemplate>30 </sette R.value>31 </setter>32 </Style>

Logical lookup of the background parent TabControl

Note that TabItem does not close itself, The closure in this case is actually removed from the items collection of his parent TabControl. And when the size of the parent TabControl changes, register the event to change the width of each item. So I decided to find its parent TabControl, Declares a private variable to add a reference to the parent.

It is possible to find its parent TabControl through the Help class visualtreehelper of the visual tree. Of course, it's not the parent. It's just TabControl.

1//<summary> 2//         recursion for parent TabControl 3//         </summary> 4//         <param name= "Reference" > Dependent objects </param> 5         //<returns>TabControl</returns> 6 private TabControl Findparenttabcontrol ( DependencyObject Reference) 7         {8             DependencyObject dobj = visualtreehelper.getparent (reference); 9             if ( Dobj = = null)                 return null;11             if (dobj.gettype () = = typeof (TabControl))                 return dobj as tabcontrol;13< C11/>else14                 return Findparenttabcontrol (dobj);         

Calculate dimensions

Since it is adaptive, there must be a normal size, only when the space is not enough to narrow down each item. The simplest way I can think of is to make a pact to put this dimension in the parent TabControl tag, so that by referring to the parent TabControl, Easily get this size.

The calculation method is to take the parent TabControl runtime width ActualWidth divided by the agreed size, take the shaping int, this is to keep the agreed width of the item number of the critical value.

This value is less than or equal to the agreed width, which is greater than the value of the parent run width divided by the number of items to find the average width, and then traverse the parent TabControl items, all assigned this mean.

It is important to note that if all items have a size that is greater than or equal to the parent's size, items will wrap and feel a bit ugly. So I took the operation of the parent run width-5, so that never arrives at the boundary, and does not break the line.

But can also rewrite TabControl control template, put Hrader container replaced StackPanel will not change line, I just think the above method is relatively simple.

Parent size Change

can be monitored through the TabControl sizechanged event. The thing to do is to recalculate the dimensions.

Close button

After removing itself from the items collection in the parent TabControl, be careful to recalculate the size and remove the method of registering the SizeChanged event.

Finally, attach the Code Adaptive tab that can be closed

This effect is more common, you may have already done, have a better idea hope you can share it, we progress together

WPF adaptive can close TabControl browser-like tabs (GO)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.