mirror of
https://github.com/gyurix1968/guacamole-client.git
synced 2025-09-06 13:17:41 +00:00
GUACAMOLE-680: Refactor repeated modal structures to common directive.
This commit is contained in:
@@ -69,6 +69,46 @@ angular.module('index').controller('indexController', ['$scope', '$injector',
|
||||
*/
|
||||
$scope.expectedCredentials = null;
|
||||
|
||||
/**
|
||||
* Possible overall states of the client side of the web application.
|
||||
*
|
||||
* @enum {string}
|
||||
*/
|
||||
var ApplicationState = {
|
||||
|
||||
/**
|
||||
* The application has fully loaded but is awaiting credentials from
|
||||
* the user before proceeding.
|
||||
*/
|
||||
AWAITING_CREDENTIALS : 'awaitingCredentials',
|
||||
|
||||
/**
|
||||
* A fatal error has occurred that will prevent the client side of the
|
||||
* application from functioning properly.
|
||||
*/
|
||||
FATAL_ERROR : 'fatalError',
|
||||
|
||||
/**
|
||||
* The application has just started within the user's browser and has
|
||||
* not yet settled into any specific state.
|
||||
*/
|
||||
LOADING : 'loading',
|
||||
|
||||
/**
|
||||
* The application has fully loaded and the user has logged in
|
||||
*/
|
||||
READY : 'ready'
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
* The current overall state of the client side of the application.
|
||||
* Possible values are defined by {@link ApplicationState}.
|
||||
*
|
||||
* @type string
|
||||
*/
|
||||
$scope.applicationState = ApplicationState.LOADING;
|
||||
|
||||
/**
|
||||
* Basic page-level information.
|
||||
*/
|
||||
@@ -103,7 +143,7 @@ angular.module('index').controller('indexController', ['$scope', '$injector',
|
||||
|
||||
// Do not handle key events if not logged in or if a notification is
|
||||
// shown
|
||||
if ($scope.expectedCredentials || guacNotification.getStatus())
|
||||
if ($scope.applicationState !== ApplicationState.READY || guacNotification.getStatus())
|
||||
return true;
|
||||
|
||||
// Warn of pending keydown
|
||||
@@ -122,7 +162,7 @@ angular.module('index').controller('indexController', ['$scope', '$injector',
|
||||
|
||||
// Do not handle key events if not logged in or if a notification is
|
||||
// shown
|
||||
if ($scope.expectedCredentials || guacNotification.getStatus())
|
||||
if ($scope.applicationState !== ApplicationState.READY || guacNotification.getStatus())
|
||||
return;
|
||||
|
||||
// Warn of pending keyup
|
||||
@@ -168,32 +208,52 @@ angular.module('index').controller('indexController', ['$scope', '$injector',
|
||||
|
||||
}, true);
|
||||
|
||||
/**
|
||||
* Reloads the current route and controller, effectively forcing
|
||||
* reauthentication. If the user is not logged in, this will result in
|
||||
* the login screen appearing.
|
||||
*/
|
||||
$scope.reAuthenticate = function reAuthenticate() {
|
||||
$scope.reAuthenticating = true;
|
||||
$route.reload();
|
||||
};
|
||||
|
||||
// Display login screen if a whole new set of credentials is needed
|
||||
$scope.$on('guacInvalidCredentials', function loginInvalid(event, parameters, error) {
|
||||
|
||||
$scope.applicationState = ApplicationState.AWAITING_CREDENTIALS;
|
||||
$scope.page.title = 'APP.NAME';
|
||||
$scope.page.bodyClassName = '';
|
||||
|
||||
$scope.loginHelpText = null;
|
||||
$scope.acceptedCredentials = {};
|
||||
$scope.expectedCredentials = error.expected;
|
||||
$scope.fatalError = null;
|
||||
|
||||
});
|
||||
|
||||
// Prompt for remaining credentials if provided credentials were not enough
|
||||
$scope.$on('guacInsufficientCredentials', function loginInsufficient(event, parameters, error) {
|
||||
|
||||
$scope.applicationState = ApplicationState.AWAITING_CREDENTIALS;
|
||||
$scope.page.title = 'APP.NAME';
|
||||
$scope.page.bodyClassName = '';
|
||||
|
||||
$scope.loginHelpText = error.translatableMessage;
|
||||
$scope.acceptedCredentials = parameters;
|
||||
$scope.expectedCredentials = error.expected;
|
||||
$scope.fatalError = null;
|
||||
|
||||
});
|
||||
|
||||
// Replace absolutely all content with an error message if the page itself
|
||||
// cannot be displayed due to an error
|
||||
$scope.$on('guacFatalPageError', function fatalPageError(error) {
|
||||
|
||||
$scope.applicationState = ApplicationState.FATAL_ERROR;
|
||||
$scope.page.title = 'APP.NAME';
|
||||
$scope.page.bodyClassName = '';
|
||||
|
||||
$scope.fatalError = error;
|
||||
|
||||
});
|
||||
|
||||
// Ensure new pages always start with clear keyboard state
|
||||
@@ -209,10 +269,7 @@ angular.module('index').controller('indexController', ['$scope', '$injector',
|
||||
|
||||
// Clear login screen if route change was successful (and thus
|
||||
// login was either successful or not required)
|
||||
$scope.loginHelpText = null;
|
||||
$scope.acceptedCredentials = null;
|
||||
$scope.expectedCredentials = null;
|
||||
$scope.fatalError = null;
|
||||
$scope.applicationState = ApplicationState.READY;
|
||||
|
||||
// Set title
|
||||
var title = current.$$route.title;
|
||||
|
27
guacamole/src/main/frontend/src/app/index/styles/cloak.css
Normal file
27
guacamole/src/main/frontend/src/app/index/styles/cloak.css
Normal file
@@ -0,0 +1,27 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Hide portions of DOM by default until Angular has finished loading,
|
||||
* compiling, etc.
|
||||
*/
|
||||
|
||||
*[ng-cloak], .translate-cloak {
|
||||
display: none !important;
|
||||
}
|
@@ -17,23 +17,10 @@
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
.fatal-page-error-outer {
|
||||
display: table;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
position: fixed;
|
||||
left: 0;
|
||||
top: 0;
|
||||
.fatal-page-error-modal guac-modal {
|
||||
z-index: 30;
|
||||
}
|
||||
|
||||
.fatal-page-error-middle {
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
display: table-cell;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
.fatal-page-error {
|
||||
display: inline-block;
|
||||
width: 100%;
|
||||
|
@@ -17,25 +17,11 @@
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
.status-outer {
|
||||
display: table;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
position: fixed;
|
||||
left: 0;
|
||||
top: 0;
|
||||
.global-status-modal guac-modal {
|
||||
background: rgba(0, 0, 0, 0.5);
|
||||
z-index: 10;
|
||||
}
|
||||
|
||||
.status-middle {
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
display: table-cell;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
.status-middle .notification {
|
||||
.global-status-modal .notification {
|
||||
|
||||
width: 75%;
|
||||
max-width: 5in;
|
||||
@@ -47,34 +33,10 @@
|
||||
|
||||
}
|
||||
|
||||
.status-middle .notification .body {
|
||||
.global-status-modal .notification .body {
|
||||
margin: 1.25em;
|
||||
}
|
||||
|
||||
.status-middle .notification .buttons {
|
||||
.global-status-modal .notification .buttons {
|
||||
margin: 1em;
|
||||
}
|
||||
|
||||
/* Fade entire status area in/out based on shown status */
|
||||
|
||||
.status-outer {
|
||||
visibility: hidden;
|
||||
opacity: 0;
|
||||
transition: opacity, visibility;
|
||||
transition-duration: 0.25s;
|
||||
}
|
||||
|
||||
.shown.status-outer {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
/* Hide dialog immediately based on status */
|
||||
|
||||
.status-middle .notification {
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
.shown .status-middle .notification {
|
||||
visibility: visible;
|
||||
}
|
||||
|
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
/**
|
||||
* A directive for displaying arbitrary modal content.
|
||||
*/
|
||||
angular.module('notification').directive('guacModal', [function guacModal() {
|
||||
return {
|
||||
restrict: 'E',
|
||||
templateUrl: 'app/notification/templates/guacModal.html',
|
||||
transclude: true
|
||||
};
|
||||
}]);
|
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
guac-modal {
|
||||
display: table;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
position: fixed;
|
||||
left: 0;
|
||||
top: 0;
|
||||
z-index: 10;
|
||||
}
|
||||
|
||||
guac-modal .modal-contents {
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
display: table-cell;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
guac-modal {
|
||||
animation: fadein 0.125s linear;
|
||||
-moz-animation: fadein 0.125s linear;
|
||||
-webkit-animation: fadein 0.125s linear;
|
||||
}
|
@@ -0,0 +1,3 @@
|
||||
<div class="modal-contents">
|
||||
<ng-transclude></ng-transclude>
|
||||
</div>
|
@@ -38,41 +38,35 @@
|
||||
|
||||
<title ng-bind="page.title | translate"></title>
|
||||
</head>
|
||||
<body ng-class="page.bodyClassName">
|
||||
|
||||
<div ng-if="!fatalError">
|
||||
|
||||
<!-- Content for logged-in users -->
|
||||
<div ng-if="!expectedCredentials">
|
||||
|
||||
<!-- Global status/error dialog -->
|
||||
<div ng-class="{shown: guacNotification.getStatus()}" class="status-outer">
|
||||
<div class="status-middle">
|
||||
<guac-notification notification="guacNotification.getStatus()"></guac-notification>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="content" ng-view>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<!-- Login screen for logged-out users -->
|
||||
<guac-login ng-show="expectedCredentials"
|
||||
help-text="loginHelpText"
|
||||
form="expectedCredentials"
|
||||
values="acceptedCredentials"></guac-login>
|
||||
|
||||
</div>
|
||||
<body ng-cloak translate-cloak ng-class="page.bodyClassName" ng-switch="applicationState">
|
||||
|
||||
<!-- Absolute fatal error -->
|
||||
<div ng-if="fatalError" ng-class="{shown: fatalError}" class="fatal-page-error-outer">
|
||||
<div class="fatal-page-error-middle">
|
||||
<div class="fatal-page-error-modal" ng-switch-when="fatalError">
|
||||
<guac-modal>
|
||||
<div class="fatal-page-error">
|
||||
<h1 translate="APP.DIALOG_HEADER_ERROR"></h1>
|
||||
<p translate="APP.ERROR_PAGE_UNAVAILABLE"></p>
|
||||
</div>
|
||||
</guac-modal>
|
||||
</div>
|
||||
|
||||
<!-- Login screen for logged-out users -->
|
||||
<guac-login ng-switch-when="awaitingCredentials"
|
||||
help-text="loginHelpText"
|
||||
form="expectedCredentials"
|
||||
values="acceptedCredentials"></guac-login>
|
||||
|
||||
<!-- Content for logged-in users -->
|
||||
<div ng-switch-default>
|
||||
|
||||
<!-- Global status/error dialog -->
|
||||
<guac-modal class="global-status-modal" ng-if="guacNotification.getStatus()">
|
||||
<guac-notification notification="guacNotification.getStatus()"></guac-notification>
|
||||
</guac-modal>
|
||||
|
||||
<div id="content" ng-view>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<!-- Polyfills -->
|
||||
|
Reference in New Issue
Block a user