Skip to content

Commit

Permalink
feat(tab-nav-bar): add initial functionality of tab nav bar (#1589)
Browse files Browse the repository at this point in the history
  • Loading branch information
andrewseguin authored and jelbourn committed Oct 26, 2016
1 parent 9e849cf commit 572b36e
Show file tree
Hide file tree
Showing 19 changed files with 329 additions and 83 deletions.
6 changes: 2 additions & 4 deletions src/demo-app/demo-app-module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,7 @@ import {SidenavDemo} from './sidenav/sidenav-demo';
import {SnackBarDemo} from './snack-bar/snack-bar-demo';
import {PortalDemo, ScienceJoke} from './portal/portal-demo';
import {MenuDemo} from './menu/menu-demo';
import {TabsDemo} from './tabs/tab-group-demo';


import {TabsDemoModule} from './tabs/tabs-demo.module';

@NgModule({
imports: [
Expand All @@ -43,6 +41,7 @@ import {TabsDemo} from './tabs/tab-group-demo';
HttpModule,
RouterModule.forRoot(DEMO_APP_ROUTES),
MaterialModule.forRoot(),
TabsDemoModule,
],
declarations: [
BaselineDemo,
Expand Down Expand Up @@ -76,7 +75,6 @@ import {TabsDemo} from './tabs/tab-group-demo';
SliderDemo,
SlideToggleDemo,
SpagettiPanel,
TabsDemo,
ToolbarDemo,
TooltipDemo,
],
Expand Down
6 changes: 3 additions & 3 deletions src/demo-app/demo-app/routes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import {Home} from './demo-app';
import {ButtonDemo} from '../button/button-demo';
import {BaselineDemo} from '../baseline/baseline-demo';
import {ButtonToggleDemo} from '../button-toggle/button-toggle-demo';
import {TabsDemo} from '../tabs/tab-group-demo';
import {TabsDemo} from '../tabs/tabs-demo';
import {GridListDemo} from '../grid-list/grid-list-demo';
import {GesturesDemo} from '../gestures/gestures-demo';
import {LiveAnnouncerDemo} from '../live-announcer/live-announcer-demo';
Expand All @@ -27,7 +27,7 @@ import {RippleDemo} from '../ripple/ripple-demo';
import {DialogDemo} from '../dialog/dialog-demo';
import {TooltipDemo} from '../tooltip/tooltip-demo';
import {SnackBarDemo} from '../snack-bar/snack-bar-demo';

import {TABS_DEMO_ROUTES} from '../tabs/routes';

export const DEMO_APP_ROUTES: Routes = [
{path: '', component: Home},
Expand All @@ -51,7 +51,7 @@ export const DEMO_APP_ROUTES: Routes = [
{path: 'live-announcer', component: LiveAnnouncerDemo},
{path: 'gestures', component: GesturesDemo},
{path: 'grid-list', component: GridListDemo},
{path: 'tabs', component: TabsDemo},
{path: 'tabs', component: TabsDemo, children: TABS_DEMO_ROUTES},
{path: 'button-toggle', component: ButtonToggleDemo},
{path: 'baseline', component: BaselineDemo},
{path: 'ripple', component: RippleDemo},
Expand Down
10 changes: 10 additions & 0 deletions src/demo-app/tabs/routes.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import {Routes} from '@angular/router';

import {SunnyTabContent, RainyTabContent, FoggyTabContent} from '../tabs/tabs-demo';

export const TABS_DEMO_ROUTES: Routes = [
{path: '', redirectTo: 'sunny-tab', pathMatch: 'full'},
{path: 'sunny-tab', component: SunnyTabContent},
{path: 'rainy-tab', component: RainyTabContent},
{path: 'foggy-tab', component: FoggyTabContent},
];
9 changes: 0 additions & 9 deletions src/demo-app/tabs/tab-group-demo.scss

This file was deleted.

26 changes: 0 additions & 26 deletions src/demo-app/tabs/tab-group-demo.ts

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,3 +1,19 @@
<h1>Tab Nav Bar</h1>

<div class="demo-nav-bar">
<nav md-tab-nav-bar aria-label="weather navigation links">
<a md-tab-link
*ngFor="let tabLink of tabLinks; let i = index"
[routerLink]="tabLink.link"
[active]="activeLinkIndex === i"
(click)="activeLinkIndex = i">
{{tabLink.label}}
</a>
</nav>
<router-outlet></router-outlet>
</div>


<h1>Tab Group Demo</h1>

<md-tab-group class="demo-tab-group">
Expand All @@ -13,6 +29,7 @@ <h1>Tab Group Demo</h1>
</md-tab>
</md-tab-group>


<h1>Async Tabs</h1>

<md-tab-group class="demo-tab-group">
Expand Down
23 changes: 23 additions & 0 deletions src/demo-app/tabs/tabs-demo.module.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import {NgModule} from '@angular/core';
import {MaterialModule} from '@angular/material';
import {FormsModule} from '@angular/forms';
import {BrowserModule} from '@angular/platform-browser';
import {RouterModule} from '@angular/router';

import {TabsDemo, SunnyTabContent, RainyTabContent, FoggyTabContent} from './tabs-demo';

@NgModule({
imports: [
FormsModule,
BrowserModule,
MaterialModule,
RouterModule,
],
declarations: [
TabsDemo,
SunnyTabContent,
RainyTabContent,
FoggyTabContent,
]
})
export class TabsDemoModule {}
22 changes: 22 additions & 0 deletions src/demo-app/tabs/tabs-demo.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
.demo-nav-bar {
border: 1px solid #e0e0e0;
[md-tab-nav-bar] {
background: #f9f9f9;
}
sunny-routed-content,
rainy-routed-content,
foggy-routed-content {
display: block;
padding: 12px;
}
}

.demo-tab-group {
border: 1px solid #e0e0e0;
.md-tab-header {
background: #f9f9f9;
}
.md-tab-body {
padding: 12px;
}
}
65 changes: 65 additions & 0 deletions src/demo-app/tabs/tabs-demo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
import {Component, ViewEncapsulation} from '@angular/core';
import {Router} from '@angular/router';
import {Observable} from 'rxjs/Observable';

@Component({
moduleId: module.id,
selector: 'tabs-demo',
templateUrl: 'tabs-demo.html',
styleUrls: ['tabs-demo.css'],
encapsulation: ViewEncapsulation.None,
})
export class TabsDemo {
tabLinks = [
{ label: 'Sun', link: 'sunny-tab'},
{ label: 'Rain', link: 'rainy-tab'},
{ label: 'Fog', link: 'foggy-tab'},
];
activeLinkIndex = 0;

tabs = [
{ label: 'Tab One', content: 'This is the body of the first tab' },
{ label: 'Tab Two', content: 'This is the body of the second tab' },
{ label: 'Tab Three', content: 'This is the body of the third tab' },
];

asyncTabs: Observable<any>;

constructor(private router: Router) {
this.asyncTabs = Observable.create((observer: any) => {
setTimeout(() => {
observer.next(this.tabs);
}, 1000);
});

// Initialize the index by checking if a tab link is contained in the url.
// This is not an ideal check and can be removed if routerLink exposes if it is active.
// https://github.com/angular/angular/pull/12525
this.activeLinkIndex =
this.tabLinks.findIndex(routedTab => router.url.indexOf(routedTab.link) != -1);
}
}


@Component({
moduleId: module.id,
selector: 'sunny-routed-content',
template: 'This is the routed body of the sunny tab.',
})
export class SunnyTabContent {}


@Component({
moduleId: module.id,
selector: 'rainy-routed-content',
template: 'This is the routed body of the rainy tab.',
})
export class RainyTabContent {}


@Component({
moduleId: module.id,
selector: 'foggy-routed-content',
template: 'This is the routed body of the foggy tab.',
})
export class FoggyTabContent {}
1 change: 1 addition & 0 deletions src/lib/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,6 @@ export * from './slider/index';
export * from './slide-toggle/index';
export * from './snack-bar/index';
export * from './tabs/index';
export * from './tabs/tab-nav-bar/index';
export * from './toolbar/index';
export * from './tooltip/index';
40 changes: 40 additions & 0 deletions src/lib/tabs/_tabs-common.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
@import '../core/style/variables';

$md-tab-bar-height: 48px !default;

// Mixin styles for labels that are contained within the tab header.
@mixin tab-label {
line-height: $md-tab-bar-height;
height: $md-tab-bar-height;
padding: 0 12px;
font-size: $md-body-font-size-base;
font-family: $md-font-family;
font-weight: 500;
cursor: pointer;
box-sizing: border-box;
color: currentColor;
opacity: 0.6;
min-width: 160px;
text-align: center;
&:focus {
outline: none;
opacity: 1;
}
}

// Mixin styles for the top section of the view; contains the tab labels.
@mixin tab-header {
overflow: hidden;
position: relative;
display: flex;
flex-direction: row;
flex-shrink: 0;
}

// Mixin styles for the ink bar that displays near the active tab in the header.
@mixin ink-bar {
position: absolute;
bottom: 0;
height: 2px;
transition: 350ms ease-out;
}
3 changes: 2 additions & 1 deletion src/lib/tabs/_tabs-theme.scss
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,8 @@
$warn: map-get($theme, warn);
$background: map-get($theme, background);
$foreground: map-get($theme, foreground);


[md-tab-nav-bar],
.md-tab-header {
border-bottom: 1px solid md-color($background, status-bar);
}
Expand Down
49 changes: 13 additions & 36 deletions src/lib/tabs/tab-group.scss
Original file line number Diff line number Diff line change
@@ -1,41 +1,20 @@
@import '../core/style/variables';


$md-tab-bar-height: 48px !default;
@import 'tabs-common';

:host {
display: flex;
flex-direction: column;
font-family: $md-font-family;
}

// The top section of the view; contains the tab labels
// Styling for the heading containing the tab labels
.md-tab-header {
overflow: hidden;
position: relative;
display: flex;
flex-direction: row;
flex-shrink: 0;
@include tab-header;
}

// Wraps each tab label
// Wraps each tab label
.md-tab-label {
line-height: $md-tab-bar-height;
height: $md-tab-bar-height;
padding: 0 12px;
font-size: $md-body-font-size-base;
font-family: $md-font-family;
font-weight: 500;
cursor: pointer;
box-sizing: border-box;
color: currentColor;
opacity: 0.6;
min-width: 160px;
text-align: center;
&:focus {
outline: none;
opacity: 1;
}
@include tab-label;
}

@media ($md-xsmall) {
Expand All @@ -44,9 +23,9 @@ $md-tab-bar-height: 48px !default;
}
}

.md-tab-disabled {
cursor: default;
pointer-events: none;
// The ink bar that displays next to the active tab
md-ink-bar {
@include ink-bar;
}

// The bottom section of the view; contains the tab bodies
Expand All @@ -69,10 +48,8 @@ $md-tab-bar-height: 48px !default;
}
}

// The colored bar that underlines the active tab
md-ink-bar {
position: absolute;
bottom: 0;
height: 2px;
transition: 350ms ease-out;
}
// Styling for any tab that is marked disabled
.md-tab-disabled {
cursor: default;
pointer-events: none;
}
1 change: 1 addition & 0 deletions src/lib/tabs/tab-nav-bar/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export * from './tab-nav-bar';
2 changes: 2 additions & 0 deletions src/lib/tabs/tab-nav-bar/tab-nav-bar.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
<ng-content></ng-content>
<md-ink-bar></md-ink-bar>
Loading

0 comments on commit 572b36e

Please sign in to comment.