| Index: chrome/browser/resources/login/screen.js
|
| diff --git a/chrome/browser/resources/login/screen.js b/chrome/browser/resources/login/screen.js
|
| index fa03371f6a3d8384c9a25ee55d0c35e505250a34..f557417861f678e109bed7a68e5d4f8a47326261 100644
|
| --- a/chrome/browser/resources/login/screen.js
|
| +++ b/chrome/browser/resources/login/screen.js
|
| @@ -8,11 +8,60 @@
|
| cr.define('login', function() {
|
| var Screen = cr.ui.define('div');
|
|
|
| + /** @const */ var CALLBACK_USER_ACTED = 'userActed';
|
| + /** @const */ var CALLBACK_CONTEXT_CHANGED = 'contextChanged';
|
| +
|
| function doNothing() {};
|
|
|
| + var querySelectorAll = HTMLDivElement.prototype.querySelectorAll;
|
| +
|
| Screen.prototype = {
|
| __proto__: HTMLDivElement.prototype,
|
|
|
| + /**
|
| + * Prefix added to sent to Chrome messages' names.
|
| + */
|
| + sendPrefix_: '',
|
| +
|
| + /**
|
| + * Context used by this screen.
|
| + */
|
| + context_: null,
|
| +
|
| + /**
|
| + * Dictionary of context observers that are methods of |this| bound to
|
| + * |this|.
|
| + */
|
| + contextObservers_: {},
|
| +
|
| + get context() {
|
| + return this.context_;
|
| + },
|
| +
|
| + /**
|
| + * Sends recent context changes to C++ handler.
|
| + */
|
| + commitContextChanges: function() {
|
| + if (!this.context_.hasChanges())
|
| + return;
|
| + this.send(CALLBACK_CONTEXT_CHANGED, this.context_.getChangesAndReset());
|
| + },
|
| +
|
| + /**
|
| + * Sends message to Chrome, adding needed prefix to message name. All
|
| + * arguments after |messageName| are packed into message parameters list.
|
| + *
|
| + * @param {string} messageName Name of message without a prefix.
|
| + * @param {...*} varArgs parameters for message.
|
| + */
|
| + send: function(messageName, varArgs) {
|
| + if (arguments.length == 0)
|
| + throw Error('Message name is not provided.');
|
| + var fullMessageName = this.sendPrefix_ + messageName;
|
| + var payload = Array.prototype.slice.call(arguments, 1);
|
| + chrome.send(fullMessageName, payload);
|
| + },
|
| +
|
| decorate: doNothing,
|
|
|
| /**
|
| @@ -28,8 +77,104 @@ cr.define('login', function() {
|
| * Called for currently active screen when screen size changed.
|
| */
|
| onWindowResize: doNothing,
|
| +
|
| + /**
|
| + * Does the following things:
|
| + * * Creates screen context.
|
| + * * Looks for elements having "alias" property and adds them as the
|
| + * proprties of the screen with name equal to value of "alias", i.e. HTML
|
| + * element <div alias="myDiv"></div> will be stored in this.myDiv.
|
| + * * Looks for buttons having "action" properties and adds click handlers
|
| + * to them. These handlers send |CALLBACK_USER_ACTED| messages to
|
| + * C++ with "action" property's value as payload.
|
| + */
|
| + initialize: function() {
|
| + this.context_ = new login.ScreenContext();
|
| + this.querySelectorAll('[alias]').forEach(function(element) {
|
| + this[element.getAttribute('alias')] = element;
|
| + }, this);
|
| + var self = this;
|
| + this.querySelectorAll('button[action]').forEach(function(button) {
|
| + button.addEventListener('click', function(e) {
|
| + var action = this.getAttribute('action');
|
| + self.send(CALLBACK_USER_ACTED, action);
|
| + e.stopPropagation();
|
| + });
|
| + });
|
| + },
|
| +
|
| + /**
|
| + * Starts observation of property with |key| of the context attached to
|
| + * current screen. This method differs from "login.ScreenContext" in that
|
| + * it automatically detects if observer is method of |this| and make
|
| + * all needed actions to make it work correctly. So it's no need for client
|
| + * to bind methods to |this| and keep resulting callback for
|
| + * |removeObserver| call:
|
| + *
|
| + * this.addContextObserver('key', this.onKeyChanged_);
|
| + * ...
|
| + * this.removeContextObserver('key', this.onKeyChanged_);
|
| + */
|
| + addContextObserver: function(key, observer) {
|
| + var realObserver = observer;
|
| + var propertyName = this.getPropertyNameOf_(observer);
|
| + if (propertyName) {
|
| + if (!this.contextObservers_.hasOwnProperty(propertyName))
|
| + this.contextObservers_[propertyName] = observer.bind(this);
|
| + realObserver = this.contextObservers_[propertyName];
|
| + }
|
| + this.context.addObserver(key, realObserver);
|
| + },
|
| +
|
| + /**
|
| + * Removes |observer| from the list of context observers. Supports not only
|
| + * regular functions but also screen methods (see comment to
|
| + * |addContextObserver|).
|
| + */
|
| + removeContextObserver: function(observer) {
|
| + var realObserver = observer;
|
| + var propertyName = this.getPropertyNameOf_(observer);
|
| + if (propertyName) {
|
| + if (!this.contextObservers_.hasOwnProperty(propertyName))
|
| + return;
|
| + realObserver = this.contextObservers_[propertyName];
|
| + delete this.contextObservers_[propertyName];
|
| + }
|
| + this.context.removeObserver(realObserver);
|
| + },
|
| +
|
| + /**
|
| + * Calls standart |querySelectorAll| method and returns its result converted
|
| + * to Array.
|
| + */
|
| + querySelectorAll: function(selector) {
|
| + var list = querySelectorAll.call(this, selector);
|
| + return Array.prototype.slice.call(list);
|
| + },
|
| +
|
| + /**
|
| + * Called when context changes are recieved from C++.
|
| + * @private
|
| + */
|
| + contextChanged_: function(diff) {
|
| + this.context.applyChanges(diff);
|
| + },
|
| +
|
| + /**
|
| + * If |value| is the value of some property of |this| returns property's
|
| + * name. Otherwise returns empty string.
|
| + * @private
|
| + */
|
| + getPropertyNameOf_: function(value) {
|
| + for (var key in this)
|
| + if (this[key] === value)
|
| + return key;
|
| + return '';
|
| + }
|
| };
|
|
|
| + Screen.CALLBACK_USER_ACTED = CALLBACK_USER_ACTED;
|
| +
|
| return {
|
| Screen: Screen
|
| };
|
| @@ -87,7 +232,12 @@ cr.define('login', function() {
|
| })(propertyName);
|
| }
|
| });
|
| + constructor.contextChanged = function() {
|
| + var screen = $(id);
|
| + screen.contextChanged_.apply(screen, arguments);
|
| + }
|
| constructor.prototype.name = function() { return id; };
|
| + constructor.prototype.sendPrefix_ = 'login.' + name + '.';
|
|
|
| constructor.register = function() {
|
| var screen = $(id);
|
|
|