Angular 2 製作 tab 元件
- 2017-01-12
- Liu, An-Chi 劉安齊
前言
tab 就是可以分頁的標籤
如果有用 Bootstrap,那要用 tab 就會很簡單。
<ul class="nav nav-tabs">
<li class="active"><a data-toggle="tab" href="#home">Home</a></li>
<li><a data-toggle="tab" href="#menu1">Menu 1</a></li>
<li><a data-toggle="tab" href="#menu2">Menu 2</a></li>
<li><a data-toggle="tab" href="#menu3">Menu 3</a></li>
</ul>
<div class="tab-content">
<div id="home" class="tab-pane fade in active">
<h3>HOME</h3>
<p>…</p>
</div>
<div id="menu1" class="tab-pane fade">
<h3>Menu 1</h3>
<p>…</p>
</div>
<div id="menu2" class="tab-pane fade">
<h3>Menu 2</h3>
<p>…</p>
</div>
<div id="menu3" class="tab-pane fade">
<h3>Menu 3</h3>
<p>…</p>
</div>
</div>
但我們今天用 Angular 2 來硬幹一個!
Tab
實現一個 tab 大概會長這樣
<tabs>
<tab>
<p>This Tab Content 1</p>
</tab>
<tab>
<p>This Tab Content 1</p>
</tab>
<tab>
<p>This Tab Content 1</p>
</tab>
</tabs>
我們並不想寫成這樣
<tabs [contents]="[...]"></tabs>
把所有 tab
的內容當變數傳遞,這會增加閱讀的難度。我們想要的是顯示層次明確的樣子,這樣的話就會用到 @ContentChild
裝飾器。
tab.ts
import {Component,Input} from '@angular/core';
@Component({
selector: 'tab',
template: <p [hidden]="!show"> <ng-content></ng-content> </p>
})
export class TabComponent {
@Input()
tabTitle:string;
show:boolean = false;
}
tabs.ts
import {Component,ContentChildren,QueryList,AfterContentInit} from '@angular/core';
import {TabComponent} from './tab';
@Component({
selector: 'tabs',
template: <ul class="tab-list"> <li *ngFor="let tab of tabs" [class.active]="selectedTab===tab" (click)="onSelect(tab)"> {{tab.tabTitle}} </li> </ul> <ng-content></ng-content>
,
styles: [`
.tab-list{
list-style:none;
overflow:hidden;
padding:0;
color: white;
}
.tab-list li{
cursor:pointer;
float:left;
width:60px;
height:30px;
line-height:30px;
text-align:center;
background-color:gray;
}
.tab-list li:hover{
background-color:#424242;
}
.tab-list li.active{
background-color:black;
}
`]
})
export class TabsComponent implements AfterContentInit {
@ContentChildren(TabComponent)
tabs:QueryList<TabComponent>;
selectedTab:TabComponent;
ngAfterContentInit() {
this.select(this.tabs.first);
}
onSelect(tab) {
this.select(tab);
}
select(tab) {
this.tabs.forEach((item)=>{
item.show = false;
});
this.selectedTab = tab;
this.selectedTab.show = true;
}
}
app.ts
import {Component,ContentChildren,QueryList} from '@angular/core';
import {TabsComponent} from './tabs';
import {TabComponent} from './tab';
@Component({
selector: 'my-app',
template: <h2>App Component</h2> <tabs> <tab tabTitle="First"> <p>This Tab Content 1</p> </tab> <tab tabTitle="Second"> <p>This Tab Content 2</p> </tab> <tab tabTitle="third"> <p>This Tab Content 3</p> </tab> </tabs>
,
directives: [TabsComponent,TabComponent]
})
export class AppComponent {
}