diff --git a/public/docs/_examples/cb-set-document-title/e2e-spec.js b/public/docs/_examples/cb-set-document-title/e2e-spec.js new file mode 100644 index 0000000000..52516f4d4b --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/e2e-spec.js @@ -0,0 +1,27 @@ +// gulp run-e2e-tests --filter=cb-set-document-title +describe('Set Document Title', function () { + + beforeAll(function () { + browser.get(''); + }); + + it('should set the document title', function () { + + var titles = [ + 'Good morning!', + 'Good afternoon!', + 'Good evening!' + ]; + + element.all( by.css( 'ul li a' ) ).each( + function iterator( element, i ) { + + element.click(); + expect( browser.getTitle() ).toEqual( titles[ i ] ); + + } + ); + + }); + +}); diff --git a/public/docs/_examples/cb-set-document-title/ts/.gitignore b/public/docs/_examples/cb-set-document-title/ts/.gitignore new file mode 100644 index 0000000000..0cd6873595 --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/ts/.gitignore @@ -0,0 +1,2 @@ +**/*.js +npm-debug.log \ No newline at end of file diff --git a/public/docs/_examples/cb-set-document-title/ts/app/app.component.ts b/public/docs/_examples/cb-set-document-title/ts/app/app.component.ts new file mode 100644 index 0000000000..692e3e75ed --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/ts/app/app.component.ts @@ -0,0 +1,29 @@ +// #docplaster +// #docregion +// Import the native Angular services. +import { Component } from 'angular2/core'; +import { Title } from 'angular2/platform/browser'; + +@Component({ +selector: 'my-app', +template: + `

+ Select a title to set on the current HTML document: +

+ + + ` +}) +// #docregion class +export class AppComponent { + public constructor(private _titleService: Title ) { } + + public setTitle( newTitle: string) { + this._titleService.setTitle( newTitle ); + } +} +// #enddocregion class diff --git a/public/docs/_examples/cb-set-document-title/ts/app/main.ts b/public/docs/_examples/cb-set-document-title/ts/app/main.ts new file mode 100644 index 0000000000..ddbb9bd57e --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/ts/app/main.ts @@ -0,0 +1,20 @@ +// #docregion +import { bootstrap } from 'angular2/platform/browser'; +import { AppComponent } from './app.component'; + +// While Angular supplies a Title service for setting the HTML document title +// it doesn't include this service as part of the default Browser platform providers. +// As such, if we want to inject it into the components within our application, +// we have to explicitly provide the Angular service in our top component. +// #docregion bootstrap-title +import { Title } from 'angular2/platform/browser'; + +bootstrap(AppComponent, [ Title ]) +// #enddocregion bootstrap-title + .then( + () => window.console.info( 'Angular finished bootstrapping your application!' ), + (error) => { + console.warn( 'Angular was not able to bootstrap your application.' ); + console.error( error ); + } + ); diff --git a/public/docs/_examples/cb-set-document-title/ts/example-config.json b/public/docs/_examples/cb-set-document-title/ts/example-config.json new file mode 100644 index 0000000000..e69de29bb2 diff --git a/public/docs/_examples/cb-set-document-title/ts/index.html b/public/docs/_examples/cb-set-document-title/ts/index.html new file mode 100644 index 0000000000..0b1a25d2c3 --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/ts/index.html @@ -0,0 +1,63 @@ + + + + + + + + + Setting The Document Title Using The Title Service + + + + + + + + + + + + + + + + + + + + +

+ Setting The Document Title Using The Title Service +

+ + + Loading app... + + + + diff --git a/public/docs/_examples/cb-set-document-title/ts/plnkr.json b/public/docs/_examples/cb-set-document-title/ts/plnkr.json new file mode 100644 index 0000000000..0131610c20 --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/ts/plnkr.json @@ -0,0 +1,9 @@ +{ + "description": "Set The Document Title In Angular 2", + "files": [ + "!**/*.d.ts", + "!**/*.js", + "!**/*.[1].*" + ], + "tags": [ "cookbook" ] +} diff --git a/public/docs/_examples/cb-set-document-title/ts/sample.css b/public/docs/_examples/cb-set-document-title/ts/sample.css new file mode 100644 index 0000000000..13acd31061 --- /dev/null +++ b/public/docs/_examples/cb-set-document-title/ts/sample.css @@ -0,0 +1,4 @@ +a { + color: #607D8B ; + text-decoration: underline ; +} diff --git a/public/docs/dart/latest/cookbook/_data.json b/public/docs/dart/latest/cookbook/_data.json index ce8315d497..2c28e02169 100644 --- a/public/docs/dart/latest/cookbook/_data.json +++ b/public/docs/dart/latest/cookbook/_data.json @@ -4,14 +4,14 @@ "navTitle": "Overview", "intro": "A collection of recipes for common Angular application scenarios" }, - + "a1-a2-quick-reference": { "title": "Angular 1 to 2 Quick Reference", "navTitle": "Angular 1 to 2 Quick Ref", "intro": "Learn how Angular 1 concepts and techniques map to Angular 2", "hide": true }, - + "component-communication": { "title": "Component Interaction", "intro": "Share information between different directives and components" @@ -22,16 +22,21 @@ "intro": "Techniques for Dependency Injection", "hide": true }, - + "dynamic-forms": { "title": "Dynamic Form", "intro": "Render dynamic forms with NgFormModel", "hide": true }, + "set-document-title": { + "title": "Set the Document Title", + "intro": "Setting the document or window title using the Title service." + }, + "ts-to-js": { "title": "TypeScript to JavaScript", "intro": "Convert Angular 2 TypeScript examples into ES5 JavaScript", "hide": true } -} \ No newline at end of file +} diff --git a/public/docs/dart/latest/cookbook/set-document-title.jade b/public/docs/dart/latest/cookbook/set-document-title.jade new file mode 100644 index 0000000000..f8df2a84a6 --- /dev/null +++ b/public/docs/dart/latest/cookbook/set-document-title.jade @@ -0,0 +1 @@ +!= partial("../../../_includes/_ts-temp") \ No newline at end of file diff --git a/public/docs/js/latest/cookbook/_data.json b/public/docs/js/latest/cookbook/_data.json index a2040caccf..e7a2501630 100644 --- a/public/docs/js/latest/cookbook/_data.json +++ b/public/docs/js/latest/cookbook/_data.json @@ -20,12 +20,17 @@ "title": "Dependency Injection", "intro": "Techniques for Dependency Injection" }, - + "dynamic-forms": { "title": "Dynamic Form", "intro": "Render dynamic forms with NgFormModel" }, + "set-document-title": { + "title": "Set the Document Title", + "intro": "Setting the document or window title using the Title service." + }, + "ts-to-js": { "title": "TypeScript to JavaScript", "intro": "Convert Angular 2 TypeScript examples into ES5 JavaScript" diff --git a/public/docs/js/latest/cookbook/set-document-title.jade b/public/docs/js/latest/cookbook/set-document-title.jade new file mode 100644 index 0000000000..f8df2a84a6 --- /dev/null +++ b/public/docs/js/latest/cookbook/set-document-title.jade @@ -0,0 +1 @@ +!= partial("../../../_includes/_ts-temp") \ No newline at end of file diff --git a/public/docs/ts/latest/cookbook/_data.json b/public/docs/ts/latest/cookbook/_data.json index e4363318ef..211e12bfd4 100644 --- a/public/docs/ts/latest/cookbook/_data.json +++ b/public/docs/ts/latest/cookbook/_data.json @@ -4,13 +4,13 @@ "navTitle": "Overview", "description": "A collection of recipes for common Angular application scenarios" }, - + "a1-a2-quick-reference": { "title": "Angular 1 to 2 Quick Reference", "navTitle": "Angular 1 to 2 Quick Ref", "intro": "Learn how Angular 1 concepts and techniques map to Angular 2" }, - + "component-communication": { "title": "Component Interaction", "intro": "Share information between different directives and components" @@ -26,6 +26,11 @@ "intro": "Render dynamic forms with NgFormModel" }, + "set-document-title": { + "title": "Set the Document Title", + "intro": "Setting the document or window title using the Title service." + }, + "ts-to-js": { "title": "TypeScript to JavaScript", "intro": "Convert Angular 2 TypeScript examples into ES5 JavaScript" diff --git a/public/docs/ts/latest/cookbook/set-document-title.jade b/public/docs/ts/latest/cookbook/set-document-title.jade new file mode 100644 index 0000000000..13ff40a408 --- /dev/null +++ b/public/docs/ts/latest/cookbook/set-document-title.jade @@ -0,0 +1,90 @@ +include ../_util-fns + +a(id='top') +:marked + Our app should be able to make the browser title bar say whatever we want it to say. + This cookbook explains how to do it. +:marked + **See the [live example](/resources/live-examples/cb-set-document-title/ts/plnkr.html)**. +.l-sub-section + img(src='/resources/images/devguide/plunker-separate-window-button.png' alt="pop out the window" align="right" style="margin-right:-20px") + :marked + To see the browser Title bar changes, + pop out the preview window by clicking the blue 'X' button in the upper right corner. +:marked + ## The problem with *<title>* + + The obvious approach is to bind a property of the component to the HTML `` like this: +code-example(format='') + <title>{{This_Does_Not_Work}}</title> +:marked + Sorry but that won't work. + The root component of our application is an element contained within the `<body>` tag. + The HTML `<title>` is in the document `<head>`, outside the body, making it inaccessible to Angular data binding. + + We could grab the browser `document` object and set the title manually. + That's dirty and undermines our chances of running the app outside of a browser someday. +.l-sub-section + :marked + That's a major Angular architectural goal. It may not seem important to us right now. + But why squander that future just to set the title bar? + +:marked + ## Use the *Title* service + Fortunately, Angular 2 bridges the gap by providing a `Title` service as part of the *Browser platform*. + The [Title](../api//platform/browser/Title-class.html) service is a simple class that provides an API + for getting and setting the current HTML document title: + + * `getTitle() : string` — Gets the title of the current HTML document. + * `setTitle( newTitle : string )` — Sets the title of the current HTML document. + + While this class is part of the Browser platform package, it is *not part of the default Browser + platform providers* that Angular loads automatically. + This means as we bootstrap our application using the Browser platform `boostrap()` + function, we'll also have to include `Title` service explicitly as one of the bootstrap providers: + ++makeExample( "cb-set-document-title/ts/app/main.ts", "bootstrap-title", "app/main.ts (provide Title service)" )(format='.') +:marked + Once we've explicitly provided the `Title` service we can then inject the `Title` service into any of our + custom application components and services. + + Let's inject the `Title` service into the root `AppComponent` and expose a bindable `setTitle` method that calls it: + ++makeExample( "cb-set-document-title/ts/app/app.component.ts", "class", "app/app.component.ts (class)" )(format='.') +:marked + We bind that method to three anchor tags and, voilĂ ! +figure.image-display + img(src="/resources/images/cookbooks/set-document-title/set-title-anim.gif" alt="Set title") + +:marked + Here's the complete solution + ++makeTabs( + `cb-set-document-title/ts/app/main.ts, + cb-set-document-title/ts/app/app.component.ts`, + '', + 'app/main.ts, app/app.component.ts' ) + +// + Todo: tie this back to the router so we can see how to use this Title service to (re)set the title + that appears in the window navigation history and shows up in the back/forward buttons + during routing. + + See https://github.com/angular/angular/issues/7630#issuecomment-198328802 + +.l-main-section +:marked + ## Why we provide the *Title* service in *bootstrap* + + We generally recommended providing application-wide services in the root application component, `AppComponent`. + + Here we recommend registering the title service during bootstrapping, + a location we reserve for configuring the runtime Angular enviroment. + + That's exactly what we're doing. + The `Title` service is part of the Angular *browser platform*. + If we bootstrap our application into a different platform, + we'll have to provide a different `Title` service that understands the concept of a "document title" for that specific platform. + Ideally the application itself neither knows nor cares about the runtime environment. +:marked + [Back to top](#top) diff --git a/public/resources/images/cookbooks/set-document-title/set-title-anim.gif b/public/resources/images/cookbooks/set-document-title/set-title-anim.gif new file mode 100644 index 0000000000..41e8a0e2da Binary files /dev/null and b/public/resources/images/cookbooks/set-document-title/set-title-anim.gif differ