Listen
This commit is contained in:
parent
45d41c6dac
commit
a6835bb900
6 changed files with 72 additions and 31 deletions
|
@ -1,6 +1,6 @@
|
||||||
# angel_route
|
# angel_route
|
||||||
|
|
||||||
![version 1.0.2](https://img.shields.io/badge/version-1.0.2-brightgreen.svg)
|
![version 1.0.3](https://img.shields.io/badge/version-1.0.3-brightgreen.svg)
|
||||||
![build status](https://travis-ci.org/angel-dart/route.svg)
|
![build status](https://travis-ci.org/angel-dart/route.svg)
|
||||||
|
|
||||||
A powerful, isomorphic routing library for Dart.
|
A powerful, isomorphic routing library for Dart.
|
||||||
|
@ -131,6 +131,8 @@ main() {
|
||||||
throw 404;
|
throw 404;
|
||||||
else route.state['foo'] = 'bar';
|
else route.state['foo'] = 'bar';
|
||||||
});
|
});
|
||||||
|
|
||||||
|
router.listen(); // Start listening
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
|
@ -1,8 +1,10 @@
|
||||||
import 'dart:async' show Stream, StreamController;
|
import 'dart:async' show Stream, StreamController;
|
||||||
import 'dart:html' show AnchorElement, window;
|
import 'dart:html';
|
||||||
import 'angel_route.dart';
|
import 'angel_route.dart';
|
||||||
|
import 'package:path/path.dart' as p;
|
||||||
|
|
||||||
final RegExp _hash = new RegExp(r'^#/');
|
final RegExp _hash = new RegExp(r'^#/');
|
||||||
|
final RegExp _straySlashes = new RegExp(r'(^/+)|(/+$)');
|
||||||
|
|
||||||
/// A variation of the [Router] support both hash routing and push state.
|
/// A variation of the [Router] support both hash routing and push state.
|
||||||
abstract class BrowserRouter extends Router {
|
abstract class BrowserRouter extends Router {
|
||||||
|
@ -14,7 +16,7 @@ abstract class BrowserRouter extends Router {
|
||||||
|
|
||||||
/// Set `hash` to true to use hash routing instead of push state.
|
/// Set `hash` to true to use hash routing instead of push state.
|
||||||
/// `listen` as `true` will call `listen` after initialization.
|
/// `listen` as `true` will call `listen` after initialization.
|
||||||
factory BrowserRouter({bool hash: false, bool listen: true}) {
|
factory BrowserRouter({bool hash: false, bool listen: false}) {
|
||||||
return hash
|
return hash
|
||||||
? new _HashRouter(listen: listen)
|
? new _HashRouter(listen: listen)
|
||||||
: new _PushStateRouter(listen: listen);
|
: new _PushStateRouter(listen: listen);
|
||||||
|
@ -30,6 +32,9 @@ abstract class BrowserRouter extends Router {
|
||||||
/// This always navigates to an absolute path.
|
/// This always navigates to an absolute path.
|
||||||
void go(List linkParams);
|
void go(List linkParams);
|
||||||
|
|
||||||
|
// Handles a route path, manually.
|
||||||
|
// void handle(String path);
|
||||||
|
|
||||||
/// Begins listen for location changes.
|
/// Begins listen for location changes.
|
||||||
void listen();
|
void listen();
|
||||||
|
|
||||||
|
@ -88,34 +93,59 @@ class _HashRouter extends _BrowserRouterImpl {
|
||||||
window.location.hash = '#$uri';
|
window.location.hash = '#$uri';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void handleHash([_]) {
|
||||||
|
final path = window.location.hash.replaceAll(_hash, '');
|
||||||
|
final resolved = resolveAbsolute(path);
|
||||||
|
|
||||||
|
if (resolved == null) {
|
||||||
|
_onResolve.add(null);
|
||||||
|
_onRoute.add(_current = null);
|
||||||
|
} else if (resolved != null && resolved.route != _current) {
|
||||||
|
_onResolve.add(resolved);
|
||||||
|
_onRoute.add(_current = resolved.route);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void handlePath(String path) {
|
||||||
|
final resolved = resolveAbsolute(path);
|
||||||
|
|
||||||
|
if (resolved == null) {
|
||||||
|
_onResolve.add(null);
|
||||||
|
_onRoute.add(_current = null);
|
||||||
|
} else if (resolved != null && resolved.route != _current) {
|
||||||
|
_onResolve.add(resolved);
|
||||||
|
_onRoute.add(_current = resolved.route);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void listen() {
|
void listen() {
|
||||||
void handleHash([_]) {
|
|
||||||
final path = window.location.hash.replaceAll(_hash, '');
|
|
||||||
final resolved = resolveAbsolute(path);
|
|
||||||
|
|
||||||
if (resolved == null) {
|
|
||||||
_onResolve.add(null);
|
|
||||||
_onRoute.add(_current = null);
|
|
||||||
} else if (resolved != null && resolved.route != _current) {
|
|
||||||
_onResolve.add(resolved);
|
|
||||||
_onRoute.add(_current = resolved.route);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
window.onHashChange.listen(handleHash);
|
window.onHashChange.listen(handleHash);
|
||||||
handleHash();
|
handleHash();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class _PushStateRouter extends _BrowserRouterImpl {
|
class _PushStateRouter extends _BrowserRouterImpl {
|
||||||
|
String _basePath;
|
||||||
|
|
||||||
_PushStateRouter({bool listen, Route root}) : super(listen: listen) {
|
_PushStateRouter({bool listen, Route root}) : super(listen: listen) {
|
||||||
|
var $base = window.document.querySelector('base[href]') as BaseElement;
|
||||||
|
|
||||||
|
if ($base?.href?.isNotEmpty != true)
|
||||||
|
throw new StateError(
|
||||||
|
'You must have a <base href="<base-url-here>"> element present in your document to run the push state router.');
|
||||||
|
_basePath = $base.href.replaceAll(_straySlashes, '');
|
||||||
if (listen) this.listen();
|
if (listen) this.listen();
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void _goTo(String uri) {
|
void _goTo(String uri) {
|
||||||
final resolved = resolveAbsolute(uri);
|
final resolved = resolveAbsolute(uri);
|
||||||
|
var relativeUri = uri;
|
||||||
|
|
||||||
|
if (_basePath?.isNotEmpty == true) {
|
||||||
|
relativeUri = p.join(_basePath, uri.replaceAll(_straySlashes, ''));
|
||||||
|
}
|
||||||
|
|
||||||
if (resolved == null) {
|
if (resolved == null) {
|
||||||
_onResolve.add(null);
|
_onResolve.add(null);
|
||||||
|
@ -125,30 +155,34 @@ class _PushStateRouter extends _BrowserRouterImpl {
|
||||||
window.history.pushState(
|
window.history.pushState(
|
||||||
{'path': route.path, 'params': {}, 'properties': properties},
|
{'path': route.path, 'params': {}, 'properties': properties},
|
||||||
route.name ?? route.path,
|
route.name ?? route.path,
|
||||||
uri);
|
relativeUri);
|
||||||
_onResolve.add(resolved);
|
_onResolve.add(resolved);
|
||||||
_onRoute.add(_current = route);
|
_onRoute.add(_current = route);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
void handleState(state) {
|
||||||
void listen() {
|
if (state is Map && state.containsKey('path')) {
|
||||||
void handleState(state) {
|
var path = state['path'];
|
||||||
if (state is Map && state.containsKey('path')) {
|
final resolved = resolveAbsolute(path);
|
||||||
final resolved = resolveAbsolute(state['path']);
|
|
||||||
|
|
||||||
if (resolved != null && resolved.route != _current) {
|
if (resolved != null && resolved.route != _current) {
|
||||||
properties.addAll(state['properties'] ?? {});
|
properties.addAll(state['properties'] ?? {});
|
||||||
_onResolve.add(resolved);
|
_onResolve.add(resolved);
|
||||||
_onRoute.add(_current = resolved.route
|
_onRoute.add(_current = resolved.route
|
||||||
..state.properties.addAll(state['params'] ?? {}));
|
..state.properties.addAll(state['params'] ?? {}));
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
_onResolve.add(null);
|
_onResolve.add(null);
|
||||||
_onRoute.add(_current = null);
|
_onRoute.add(_current = null);
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
_onResolve.add(null);
|
||||||
|
_onRoute.add(_current = null);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void listen() {
|
||||||
window.onPopState.listen((e) {
|
window.onPopState.listen((e) {
|
||||||
handleState(e.state);
|
handleState(e.state);
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
name: angel_route
|
name: angel_route
|
||||||
description: A powerful, isomorphic routing library for Dart.
|
description: A powerful, isomorphic routing library for Dart.
|
||||||
version: 1.0.2
|
version: 1.0.3
|
||||||
author: Tobe O <thosakwe@gmail.com>
|
author: Tobe O <thosakwe@gmail.com>
|
||||||
homepage: https://github.com/angel-dart/angel_route
|
homepage: https://github.com/angel-dart/angel_route
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
|
|
2
repubspec.yaml
Normal file
2
repubspec.yaml
Normal file
|
@ -0,0 +1,2 @@
|
||||||
|
push_state:
|
||||||
|
base: push_state/basic.html
|
|
@ -1,6 +1,7 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
|
<base href="/push_state">
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<meta name="viewport"
|
<meta name="viewport"
|
||||||
content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
|
content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
|
||||||
|
@ -25,7 +26,7 @@
|
||||||
<ul id="handlers">
|
<ul id="handlers">
|
||||||
<li>(empty)</li>
|
<li>(empty)</li>
|
||||||
</ul>
|
</ul>
|
||||||
<script src="basic.dart" type="application/dart"></script>
|
<script src="/push_state/basic.dart" type="application/dart"></script>
|
||||||
<script src="packages/browser/dart.js"></script>
|
<script src="packages/browser/dart.js"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
|
@ -31,5 +31,7 @@ basic(BrowserRouter router) {
|
||||||
|
|
||||||
router.get('c', 'c handler');
|
router.get('c', 'c handler');
|
||||||
|
|
||||||
router.dumpTree();
|
router
|
||||||
|
..dumpTree()
|
||||||
|
..listen();
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue