Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(89)

Side by Side Diff: third_party/pkg/angular/lib/routing/module.dart

Issue 124053002: Adding Angular and dependent packages for testing (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 6 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 /**
2 * Routing library makes it easier to build large single-page application. The
3 * library lets you map the browser address bar to semantic structure of your
4 * application and keeps them in sync.
5 *
6 * Angular uses [route_hierarchical] package to define application routes and
7 * provides custom tools that it easier to use routing with Angular templates.
8 *
9 * Lets consider a simple recipe book application. The application might have
10 * the following pages:
11 *
12 * * recipes list/search
13 * * add new recipe
14 * * view recipe
15 * * edit recipe
16 *
17 * Each of those pages can be represented by an address:
18 *
19 * * `/recipes`
20 * * `/addRecipe`
21 * * `/recipe/:recipeId/view`
22 * * `/recipe/:recipeId/edit`
23 *
24 *
25 * Lets try to define those routes in Angular. To get started we need to
26 * provide an implementation of [RouteInitializer] interface.
27 *
28 * class RecipesRouteInitializer implements RouteInitializer {
29 * void init(Router router, ViewFactory view) {
30 * // define routes here.
31 * }
32 * }
33 *
34 * var module = new Module()
35 * ..type(RouteInitializer, implementedBy: RecipesRouteInitializer);
36 *
37 * Lets see how we could define our routes using the routing framework:
38 *
39 * class RecipesRouteInitializer implements RouteInitializer {
40 * void init(Router router, ViewFactory view) {
41 * router
42 * ..addRoute(
43 * name: 'recipes',
44 * path: '/recipes',
45 * enter: view('recipes.html'))
46 * ..addRoute(
47 * name: 'addRecipe',
48 * path: '/addRecipe',
49 * enter: view('addRecipe.html'))
50 * ..addRoute(
51 * name: 'viewRecipe',
52 * path: '/recipe/:recipeId/view',
53 * enter: view('viewRecipe.html'))
54 * ..addRoute(
55 * name: 'editRecipe',
56 * path: '/recipe/:recipeId/edit',
57 * enter: view('editRecipe.html'));
58 * }
59 * }
60 *
61 * We defined 4 routes and for each route we set views (templates) to be
62 * displayed when that route is "entered". For example, when the browser URL
63 * is set to `/recipes`, the `recipes.html` will be displayed.
64 *
65 * You have to tell Angular where to load views by putting `<ng-view>` tag in
66 * you template.
67 *
68 * Notice that `viewRecipe` and `editRecipe` route paths have `recipeId`
69 * parameter in them. We need to be able to get hold of that parameter in
70 * order to know which recipe to load. Lets consider the following
71 * `viewRecipe.html`.
72 *
73 * <view-recipe></view-recipe>
74 *
75 * The template contains a custom `view-recipe` component that handles the
76 * displaying of the recipe. Now, our `view-recipe` can inject [RouteProvider]
77 * to get hold of the route and its parameters. It might look like this:
78 *
79 * @NgComponent(...)
80 * class ViewRecipeComponent {
81 * ViewRecipeComponent(RouteProvider routeProvider) {
82 * String recipeId = routeProvider.parameters['recipeId'];
83 * _loadRecipe(recipeId);
84 * }
85 * }
86 *
87 * [RouteProvider] and [Route] can be used to control navigation, specifically,
88 * leaving of the route. For example, lets consider "edit recipe" component:
89 *
90 * @NgComponent(...)
91 * class EditRecipeComponent implements NgDetachAware {
92 * RouteHandle route;
93 * EditRecipeComponent(RouteProvider routeProvider) {
94 * RouteHandle route = routeProvider.route.newHandle();
95 * _loadRecipe(route);
96 * route.onLeave.listen((RouteEvent event) {
97 * event.allowLeave(_checkIfOkToLeave());
98 * });
99 * }
100 *
101 * /// Check if the editor has unsaved contents and if necessary ask
102 * /// the user if OK to leave this page.
103 * Future<bool> _checkIfOkToLeave() {/* ... */}
104 *
105 * detach() {
106 * route.discard();
107 * }
108 * }
109 *
110 * [Route.onLeave] event is triggered when the browser is routed from an
111 * active route to a different route. The active route can delay and
112 * potentially veto the navigation by passing a [Future<bool>] to
113 * [RouteEvent.allowLeave].
114 *
115 * Notice that we create a [RouteHandle] for our route. [RouteHandle] are
116 * a convinient wrapper around [Route] that makes unsubscribing route events
117 * easier. For example, notice that we didn't need to manually call
118 * [StreamSubscription.cancel] for subscription to [Route.onLeave]. Calling
119 * [RouteHandle.discard] unsubscribes all listeneters created for the handle.
120 *
121 *
122 * # Hierarchical Routes
123 *
124 * The routing framework allows us to define trees of routes. In our recipes
125 * example we could have defined our routes like this:
126 *
127 * class RecipesRouteInitializer implements RouteInitializer {
128 * void init(Router router, ViewFactory view) {
129 * router
130 * ..addRoute(
131 * name: 'recipes',
132 * path: '/recipes',
133 * enter: view('recipes.html'))
134 * ..addRoute(
135 * name: 'addRecipe',
136 * path: '/addRecipe',
137 * enter: view('addRecipe.html'))
138 * ..addRoute(
139 * name: 'recipe',
140 * path: '/recipe/:recipeId',
141 * mount: (Route route) => route
142 * ..addRoute(
143 * name: 'view',
144 * path: '/view',
145 * enter: view('viewRecipe.html'))
146 * ..addRoute(
147 * name: 'edit',
148 * path: '/edit',
149 * enter: view('editRecipe.html')));
150 * }
151 * }
152 */
153 library angular.routing;
154
155 import 'dart:async';
156 import 'dart:html';
157
158 import 'package:di/di.dart';
159 import 'package:angular/angular.dart';
160 import 'package:route_hierarchical/client.dart';
161 export 'package:route_hierarchical/client.dart';
162
163 part 'routing.dart';
164 part 'ng_view.dart';
165 part 'ng_bind_route.dart';
166
167 class NgRoutingModule extends Module {
168 NgRoutingModule({bool usePushState: true}) {
169 type(NgRoutingUsePushState);
170 factory(Router, (injector) {
171 var useFragment = !injector.get(NgRoutingUsePushState).usePushState;
172 return new Router(useFragment: useFragment,
173 windowImpl: injector.get(Window));
174 });
175 type(NgRoutingHelper);
176 value(RouteProvider, null);
177 value(RouteInitializer, null);
178
179 // directives
180 value(NgViewDirective, null);
181 type(NgBindRouteDirective);
182 }
183 }
184
185 /**
186 * Allows configuration of [Router.useFragment]. By default [usePushState] is
187 * true, so router will be listen to [Window.onPopState] and route URLs like
188 * "http://host:port/foo/bar?baz=qux". Both path and query parts of the URL
189 * are used by the router. If [usePushState] is false, router will listen to
190 * [Window.onHashChange] and route URLs like
191 * "http://host:port/path#/foo/bar?baz=qux". Everything after hash (#) is used
192 * by the router.
193 */
194 @NgInjectableService()
195 class NgRoutingUsePushState {
196 final bool usePushState;
197 NgRoutingUsePushState(): usePushState = true;
198 NgRoutingUsePushState.value(this.usePushState);
199 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698