OLD | NEW |
| (Empty) |
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file | |
2 // for details. All rights reserved. Use of this source code is governed by a | |
3 // BSD-style license that can be found in the LICENSE file. | |
4 | |
5 /** | |
6 * The base class for UI state that intends to support browser history. | |
7 */ | |
8 class UIState { | |
9 /** | |
10 * The event listener we hook to the window's "popstate" event. | |
11 * This event is triggered by the back button or by the first page load. | |
12 */ | |
13 EventListener _historyTracking; | |
14 | |
15 UIState(); | |
16 | |
17 void startHistoryTracking() { | |
18 stopHistoryTracking(); | |
19 | |
20 bool firstEvent = true; | |
21 _historyTracking = EventBatch.wrap((event) { | |
22 String state = window.location.hash; | |
23 if (state.startsWith('#')) { | |
24 // TODO(jimhug): Support default argument on substring. | |
25 state = state.substring(1, state.length); | |
26 } | |
27 | |
28 if (firstEvent && state != '') { | |
29 // TODO(jmesserly): When loading a bookmark or refreshing, we replace | |
30 // the app state with a clean app state so the back button works. It | |
31 // would be better to support jumping to the previous story. | |
32 // We'd need to do some history manipulation here and some fixes to | |
33 // the views for this. | |
34 window.history.replaceState(null, document.title, '#'); | |
35 } else if (state != '') { | |
36 loadFromHistory(JSON.parse(state)); | |
37 } | |
38 firstEvent = false; | |
39 }); | |
40 | |
41 window.on.popState.add(_historyTracking); | |
42 } | |
43 | |
44 void stopHistoryTracking() { | |
45 if (_historyTracking != null) { | |
46 window.on.popState.add(_historyTracking); // remove? | |
47 } | |
48 } | |
49 | |
50 /** Pushes a state onto the browser history stack */ | |
51 void pushToHistory() { | |
52 if (_historyTracking == null) { | |
53 throw 'history tracking not started'; | |
54 } | |
55 | |
56 String state = JSON.stringify(toHistory()); | |
57 | |
58 // TODO(jmesserly): [state] should be an Object, and we should pass it to | |
59 // the state parameter instead of as a #hash URL. Right now we're working | |
60 // around b/4582542. | |
61 window.history.pushState(null, document.title, '#' + state); | |
62 } | |
63 | |
64 /** | |
65 * Serialize the state to a form suitable for storing in browser history. | |
66 */ | |
67 abstract Map<String, String> toHistory(); | |
68 | |
69 /** | |
70 * Load the UI state from the given [values]. | |
71 */ | |
72 abstract void loadFromHistory(Map<String, String> values); | |
73 } | |
OLD | NEW |