1ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// Copyright (c) 2011 The Chromium Authors. All rights reserved. 2ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// Use of this source code is governed by a BSD-style license that can be 3ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// found in the LICENSE file. 4ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 5ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// require: cr.js 6ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// require: cr/ui.js 7ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// require: cr/ui/tree.js 8ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 9ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsencr.define('chrome.sync', function() { 10ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // Allow platform specific CSS rules. 11ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // 12ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(akalin): BMM and options page does something similar, too. 13ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // Move this to util.js. 14ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (cr.isWindows) 15ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen document.documentElement.setAttribute('os', 'win'); 16ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 17ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(akalin): Create SyncNodeTree/SyncNodeTreeItem classes that 18ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // hide all these details. 19ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 20ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen /** 21ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * Gets all children of the given node and passes it to the given 22ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * callback. 23ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * @param {Object} nodeInfo The info for the node whose children we 24ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * want. 25ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * @param {Function} callback The callback to call with the list of 26ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * children. 27ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen */ 28ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen function getSyncNodeChildren(nodeInfo, callback) { 29ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var children = []; 30ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen function processChildInfo(childNodeInfo) { 31ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (!childNodeInfo) { 32ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen callback(children); 33ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen return; 34ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 35ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen children.push(childNodeInfo); 36ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen chrome.sync.getNodeById(childNodeInfo.successorId, processChildInfo); 37ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }; 38ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen chrome.sync.getNodeById(nodeInfo.firstChildId, processChildInfo); 39ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 40ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 41ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen /** 42ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * Makes a tree item from the given node info. 43ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * @param {dictionary} nodeInfo The node info to create the tree 44ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * item from. 45ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * @return {cr.ui.TreeItem} The created tree item. 46ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen */ 47ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen function makeNodeTreeItem(nodeInfo) { 48ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var treeItem = new cr.ui.TreeItem({ 49ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen label: nodeInfo.title, 50ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen detail: nodeInfo 51ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }); 52ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 53ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (nodeInfo.isFolder) { 54ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen treeItem.mayHaveChildren_ = true; 55ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 56ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // Load children asynchronously on expand. 57ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(akalin): Add a throbber while loading? 58ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen treeItem.triggeredLoad_ = false; 59ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen treeItem.addEventListener('expand', function(event) { 60ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (!treeItem.triggeredLoad_) { 61ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen getSyncNodeChildren(nodeInfo, function(children) { 62ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen for (var i = 0; i < children.length; ++i) { 63ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var childTreeItem = makeNodeTreeItem(children[i]); 64ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen treeItem.add(childTreeItem); 65ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 66ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }); 67ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen treeItem.triggeredLoad_ = true; 68ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 69ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }); 70ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } else { 71ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen treeItem.classList.add('leaf'); 72ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 73ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen return treeItem; 74ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 75ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 76ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen /** 77ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * Updates the node detail view with the info for the given node. 78ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * @param {dictionary} nodeInfo The info for the node we want to 79ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen * display. 80ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen */ 81ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen function updateNodeDetailView(nodeInfo) { 82ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var nodeBrowser = document.getElementById('node-browser'); 83ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(akalin): Get rid of this hack. 84ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (typeof nodeInfo.entry != 'string') 85ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen nodeInfo.entry = JSON.stringify(nodeInfo.entry, null, 2); 86ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen jstProcess(new JsEvalContext(nodeInfo), nodeBrowser); 87ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 88ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 89ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen function decorateSyncNodeBrowser(syncNodeBrowser) { 90ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen cr.ui.decorate(syncNodeBrowser, cr.ui.Tree); 91ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 92ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen syncNodeBrowser.addEventListener('change', function(event) { 93ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (syncNodeBrowser.selectedItem) 94ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen updateNodeDetailView(syncNodeBrowser.selectedItem.detail); 95ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }); 96ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 97ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen chrome.sync.getRootNode(function(rootNodeInfo) { 98ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var rootTreeItem = makeNodeTreeItem(rootNodeInfo); 99ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen rootTreeItem.label = 'Root'; 100ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen syncNodeBrowser.add(rootTreeItem); 101ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }); 102ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 103ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 104ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // This is needed because JsTemplate (which is needed by 105ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // updateNodeDetailView) is loaded at the end of the file after 106ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // everything else. 107ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // 108ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(akalin): Remove dependency on JsTemplate and get rid of 109ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // this. 110ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var domLoaded = false; 111ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var pendingSyncNodeBrowsers = []; 112ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen function decorateSyncNodeBrowserAfterDOMLoad(id) { 113ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen var e = document.getElementById(id); 114ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (domLoaded) { 115ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen decorateSyncNodeBrowser(e); 116ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } else { 117ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen pendingSyncNodeBrowsers.push(e); 118ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 119ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 120ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 121ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen document.addEventListener('DOMContentLoaded', function() { 122ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen for (var i = 0; i < pendingSyncNodeBrowsers.length; ++i) { 123ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen decorateSyncNodeBrowser(pendingSyncNodeBrowsers[i]); 124ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 125ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen domLoaded = true; 126ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }); 127ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 128ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen return { 129ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen decorateSyncNodeBrowser: decorateSyncNodeBrowserAfterDOMLoad 130ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen }; 131ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen}); 132