Commit d44e8a77 authored by garykac's avatar garykac Committed by Commit bot

[Chromoting] Show any startup errors in the LoadingWindow.

Show any connection errors during startup in the LoadingWindow rather
than creating a new error window for the error.

This cl also adds a new updateErrorMessage method to the MessageWindow
to update the message and reset the message window as appropriate for
an error message (disabling the spinner, updating the button label).

BUG=

Review URL: https://codereview.chromium.org/1139543002

Cr-Commit-Position: refs/heads/master@{#330022}
parent 319828dc
...@@ -189,8 +189,8 @@ remoting.AppRemotingActivity.prototype.onDisconnected = function(error) { ...@@ -189,8 +189,8 @@ remoting.AppRemotingActivity.prototype.onDisconnected = function(error) {
* @param {!remoting.Error} error * @param {!remoting.Error} error
*/ */
remoting.AppRemotingActivity.prototype.onConnectionFailed = function(error) { remoting.AppRemotingActivity.prototype.onConnectionFailed = function(error) {
remoting.LoadingWindow.close(); remoting.loadingWindow_.updateErrorMessage(
this.showErrorMessage_(error); chrome.i18n.getMessage(error.getTag()));
this.cleanup_(); this.cleanup_();
}; };
...@@ -199,7 +199,7 @@ remoting.AppRemotingActivity.prototype.onConnectionFailed = function(error) { ...@@ -199,7 +199,7 @@ remoting.AppRemotingActivity.prototype.onConnectionFailed = function(error) {
* @private * @private
*/ */
remoting.AppRemotingActivity.prototype.showErrorMessage_ = function(error) { remoting.AppRemotingActivity.prototype.showErrorMessage_ = function(error) {
console.error('Connection failed: ' + error.toString()); console.error('Error: ' + error.toString());
remoting.MessageWindow.showErrorMessage( remoting.MessageWindow.showErrorMessage(
remoting.app.getApplicationName(), remoting.app.getApplicationName(),
chrome.i18n.getMessage(error.getTag())); chrome.i18n.getMessage(error.getTag()));
......
...@@ -44,19 +44,16 @@ MessageWindowImpl.prototype.sendReply_ = function( ...@@ -44,19 +44,16 @@ MessageWindowImpl.prototype.sendReply_ = function(
}; };
/** /**
* Initializes the button with the label and the click handler. * Updates the button label text.
* Hides the button if the label is null or undefined. * Hides the button if the label is null or undefined.
* *
* @param{HTMLElement} button * @param{HTMLElement} button
* @param{?string} label * @param{?string} label
* @param{Function} clickHandler
* @private * @private
*/ */
MessageWindowImpl.prototype.initButton_ = MessageWindowImpl.prototype.updateButton_ = function(button, label) {
function(button, label, clickHandler) {
if (label) { if (label) {
button.innerText = label; button.innerText = label;
button.addEventListener('click', clickHandler, false);
} }
button.hidden = !Boolean(label); button.hidden = !Boolean(label);
}; };
...@@ -69,56 +66,77 @@ MessageWindowImpl.prototype.initButton_ = ...@@ -69,56 +66,77 @@ MessageWindowImpl.prototype.initButton_ =
* @private * @private
*/ */
MessageWindowImpl.prototype.onMessage_ = function(event) { MessageWindowImpl.prototype.onMessage_ = function(event) {
switch (event.data['command']) { var command = /** @type {string} */ (event.data['command']);
case 'show': if (command !== 'show' && command !== 'update') {
console.error('Unexpected message: ' + command);
return;
}
// Validate the message. // Validate the message.
var messageId = /** @type {number} */ (event.data['id']); var messageId = /** @type {number} */ (event.data['id']);
var title = /** @type {string} */ (event.data['title']); var title = /** @type {string} */ (event.data['title']);
var message = /** @type {string} */ (event.data['message']); var message = /** @type {string} */ (event.data['message']);
var infobox = /** @type {string} */ (event.data['infobox']); var infobox = /** @type {string} */ (event.data['infobox']);
var buttonLabel = /** @type {string} */ (event.data['buttonLabel']); var buttonLabel = /** @type {string} */ (event.data['buttonLabel']);
/** @type {string} */ var cancelButtonLabel = /** @type {string} */
var cancelButtonLabel = (event.data['cancelButtonLabel']); (event.data['cancelButtonLabel']);
var showSpinner = /** @type {boolean} */ (event.data['showSpinner']); var showSpinner = /** @type {boolean} */ (event.data['showSpinner']);
if (typeof(messageId) != 'number' ||
typeof(title) != 'string' || // Many of these fields are optional for either the 'show' or 'update'
typeof(message) != 'string' || // message. These vars are used to mark the optional fields to allow
typeof(infobox) != 'string' || // them to be undefined.
typeof(buttonLabel) != 'string' || var optionalFieldShow = command === 'show';
typeof(showSpinner) != 'boolean') { var optionalFieldUpdate = command === 'update';
console.log('Bad show message:', event.data); if (isNumber(messageId) ||
break; isString(title, optionalFieldUpdate) ||
isString(message, optionalFieldUpdate) ||
isString(infobox, optionalFieldUpdate) ||
isString(buttonLabel, optionalFieldUpdate) ||
isString(cancelButtonLabel, optionalFieldShow || optionalFieldUpdate) ||
isBoolean(showSpinner, optionalFieldUpdate) {
console.log('Bad ' + command + ' message: ' + event.data);
return;
} }
// Set the dialog text.
var button = document.getElementById('button-primary'); var button = document.getElementById('button-primary');
var cancelButton = document.getElementById('button-secondary'); var cancelButton = document.getElementById('button-secondary');
var messageDiv = document.getElementById('message'); var messageDiv = document.getElementById('message');
var infoboxDiv = document.getElementById('infobox'); var infoboxDiv = document.getElementById('infobox');
if (isString(title)) {
document.getElementById('title').innerText = title; document.getElementById('title').innerText = title;
document.querySelector('title').innerText = title; document.querySelector('title').innerText = title;
messageDiv.innerHTML = message;
if (showSpinner) {
messageDiv.classList.add('waiting');
messageDiv.classList.add('prominent');
} }
if (isString(message) {
messageDiv.innerText = message;
}
if (isString(infobox)) {
if (infobox != '') { if (infobox != '') {
infoboxDiv.innerText = infobox; infoboxDiv.innerText = infobox;
} else { } else {
infoboxDiv.hidden = true; infoboxDiv.hidden = true;
} }
}
if (isBoolean(showSpinner)) {
if (showSpinner) {
messageDiv.classList.add('waiting');
messageDiv.classList.add('prominent');
} else {
messageDiv.classList.remove('waiting');
messageDiv.classList.remove('prominent');
}
}
this.updateButton_(button, buttonLabel);
this.updateButton_(cancelButton, cancelButtonLabel);
this.initButton_( base.resizeWindowToContent(true);
button,
buttonLabel,
this.sendReply_.bind(this, event.source, messageId, 1));
this.initButton_( if (command === 'show') {
cancelButton, // Set up click-handlers for the buttons.
cancelButtonLabel, button.addEventListener(
this.sendReply_.bind(this, event.source, messageId, 0)); 'click', this.sendReply_.bind(this, event.source, messageId, 1), false);
cancelButton.addEventListener(
'click', this.sendReply_.bind(this, event.source, messageId, 0), false);
var buttonToFocus = (cancelButtonLabel) ? cancelButton : button; var buttonToFocus = (cancelButtonLabel) ? cancelButton : button;
buttonToFocus.focus(); buttonToFocus.focus();
...@@ -130,25 +148,7 @@ MessageWindowImpl.prototype.onMessage_ = function(event) { ...@@ -130,25 +148,7 @@ MessageWindowImpl.prototype.onMessage_ = function(event) {
chrome.app.window.current().onClosed.addListener( chrome.app.window.current().onClosed.addListener(
this.sendReply_.bind(this, event.source, messageId, 0)); this.sendReply_.bind(this, event.source, messageId, 0));
base.resizeWindowToContent(true);
chrome.app.window.current().show(); chrome.app.window.current().show();
break;
case 'update_message':
var message = /** @type {string} */ (event.data['message']);
if (typeof(message) != 'string') {
console.log('Bad update_message message:', event.data);
break;
}
var messageDiv = document.getElementById('message');
messageDiv.innerText = message;
base.resizeWindowToContent(true);
break;
default:
console.error('Unexpected message:', event.data);
} }
}; };
......
...@@ -41,6 +41,9 @@ remoting.MessageWindowOptions = function() { ...@@ -41,6 +41,9 @@ remoting.MessageWindowOptions = function() {
/** @type {number} */ /** @type {number} */
this.minimumWidth = 0; this.minimumWidth = 0;
/** @type {boolean} */
this.showSpinner = false;
}; };
/** /**
...@@ -151,12 +154,36 @@ remoting.MessageWindow.prototype.updateMessage = function(message) { ...@@ -151,12 +154,36 @@ remoting.MessageWindow.prototype.updateMessage = function(message) {
} }
var message_struct = { var message_struct = {
command: 'update_message', command: 'update',
message: message message: message
}; };
this.window_.postMessage(message_struct, '*'); this.window_.postMessage(message_struct, '*');
}; };
/**
* Update the message being shown in the window to the given error message.
* In addition to updating the message, any spinner is disabled and the
* button text is changed to 'OK'.
* This should only be called after the window has been shown.
*
* @param {string} message The message.
*/
remoting.MessageWindow.prototype.updateErrorMessage = function(message) {
if (!this.window_) {
this.pendingWindowOperations_.push(this.updateMessage.bind(this, message));
return;
}
var message_struct = {
command: 'update',
message: message,
buttonLabel: chrome.i18n.getMessage(/*i18n-content*/'OK'),
cancelButtonLabel: '',
showSpinner: false
};
this.window_.postMessage(message_struct, '*');
};
/** /**
* Close the message box and unregister it with the window manager. * Close the message box and unregister it with the window manager.
*/ */
......
...@@ -19,17 +19,25 @@ var isArray = function(value) { ...@@ -19,17 +19,25 @@ var isArray = function(value) {
/** /**
* @param {*} value * @param {*} value
* @param {boolean=} opt_allowUndefined True to accept undefined.
* @return {boolean} * @return {boolean}
*/ */
var isBoolean = function(value) { var isBoolean = function(value, opt_allowUndefined) {
if (opt_allowUndefined && value === 'undefined') {
return true;
}
return typeof value == 'boolean'; return typeof value == 'boolean';
}; };
/** /**
* @param {*} value * @param {*} value
* @param {boolean=} opt_allowUndefined True to accept undefined.
* @return {boolean} * @return {boolean}
*/ */
var isNumber = function(value) { var isNumber = function(value, opt_allowUndefined) {
if (opt_allowUndefined && value === 'undefined') {
return true;
}
return typeof value == 'number'; return typeof value == 'number';
}; };
...@@ -43,9 +51,13 @@ var isObject = function(value) { ...@@ -43,9 +51,13 @@ var isObject = function(value) {
/** /**
* @param {*} value * @param {*} value
* @param {boolean=} opt_allowUndefined True to accept undefined.
* @return {boolean} * @return {boolean}
*/ */
var isString = function(value) { var isString = function(value, opt_allowUndefined) {
if (opt_allowUndefined && value === 'undefined') {
return true;
}
return typeof value == 'string'; return typeof value == 'string';
}; };
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment