toolkit/modules/sessionstore/ScrollPosition.jsm

changeset 0
6474c204b198
equal deleted inserted replaced
-1:000000000000 0:4ea8324fff08
1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this file,
3 * You can obtain one at http://mozilla.org/MPL/2.0/. */
4
5 "use strict";
6
7 this.EXPORTED_SYMBOLS = ["ScrollPosition"];
8
9 const Ci = Components.interfaces;
10
11 /**
12 * It provides methods to collect and restore scroll positions for single
13 * frames and frame trees.
14 *
15 * This is a child process module.
16 */
17 this.ScrollPosition = Object.freeze({
18 /**
19 * Collects scroll position data for any given |frame| in the frame hierarchy.
20 *
21 * @param frame (DOMWindow)
22 *
23 * @return {scroll: "x,y"} e.g. {scroll: "100,200"}
24 * Returns null when there is no scroll data we want to store for the
25 * given |frame|.
26 */
27 collect: function (frame) {
28 let ifreq = frame.QueryInterface(Ci.nsIInterfaceRequestor);
29 let utils = ifreq.getInterface(Ci.nsIDOMWindowUtils);
30 let scrollX = {}, scrollY = {};
31 utils.getScrollXY(false /* no layout flush */, scrollX, scrollY);
32
33 if (scrollX.value || scrollY.value) {
34 return {scroll: scrollX.value + "," + scrollY.value};
35 }
36
37 return null;
38 },
39
40 /**
41 * Restores scroll position data for any given |frame| in the frame hierarchy.
42 *
43 * @param frame (DOMWindow)
44 * @param value (object, see collect())
45 */
46 restore: function (frame, value) {
47 let match;
48
49 if (value && (match = /(\d+),(\d+)/.exec(value))) {
50 frame.scrollTo(match[1], match[2]);
51 }
52 },
53
54 /**
55 * Restores scroll position data for the current frame hierarchy starting at
56 * |root| using the given scroll position |data|.
57 *
58 * If the given |root| frame's hierarchy doesn't match that of the given
59 * |data| object we will silently discard data for unreachable frames. We
60 * may as well assign scroll positions to the wrong frames if some were
61 * reordered or removed.
62 *
63 * @param root (DOMWindow)
64 * @param data (object)
65 * {
66 * scroll: "100,200",
67 * children: [
68 * {scroll: "100,200"},
69 * null,
70 * {scroll: "200,300", children: [ ... ]}
71 * ]
72 * }
73 */
74 restoreTree: function (root, data) {
75 if (data.hasOwnProperty("scroll")) {
76 this.restore(root, data.scroll);
77 }
78
79 if (!data.hasOwnProperty("children")) {
80 return;
81 }
82
83 let frames = root.frames;
84 data.children.forEach((child, index) => {
85 if (child && index < frames.length) {
86 this.restoreTree(frames[index], child);
87 }
88 });
89 }
90 });

mercurial