Feature/kasm 2634 UI updates (#30)

* KASM-2634 control panel UI updates

* add kasm splash background

* WIP minor tweaks

* WIP fix disabled settings, add more idle timout options

Co-authored-by: matt <matt@kasmweb.com>
This commit is contained in:
Matt McClaskey 2022-06-24 04:58:34 -04:00 committed by GitHub
parent 41e9ae92c1
commit e3991665d6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 657 additions and 489 deletions

BIN
app/images/splash.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 93 KiB

View File

@ -22,7 +22,8 @@
body {
margin:0;
padding:0;
font-family: Helvetica;
font-family: "Poppins", "Helvetica";
letter-spacing: 0.05em;
background: white url('../images/icons/kasm_logo.png') no-repeat fixed center;
height:100%;
touch-action: none;
@ -37,7 +38,7 @@ html {
}
.noVNC_disabled {
color: rgb(128, 128, 128);
color: rgb(128, 128, 128) !important;
}
/* ----------------------------------------
@ -351,8 +352,9 @@ select:active {
/* Edge misrenders animations wihthout this */
transform: translateX(0);
}
:root.noVNC_connected #noVNC_control_bar_anchor.noVNC_idle {
opacity: 0.8;
/* opacity: 0.8; */
}
#noVNC_control_bar_anchor.noVNC_right {
left: auto;
@ -365,12 +367,12 @@ select:active {
transition: 0.5s ease-in-out;
background-color: rgb(80, 89, 101);
background-color: rgb(9 2 2 / 0.6);
border-radius: 0 10px 10px 0;
border-style: inset;
border-color: rgb(255 255 255 / 0.6);
}
#noVNC_control_bar.noVNC_open {
box-shadow: 6px 6px 0px rgba(0, 0, 0, 0.5);
left: 0;
}
#noVNC_control_bar::before {
@ -400,28 +402,31 @@ select:active {
#noVNC_control_bar_handle {
position: absolute;
left: -15px;
top: 0;
transform: translateY(35px);
width: calc(100% + 30px);
height: 50px;
z-index: -1;
cursor: pointer;
border-radius: 5px;
background-color: rgb(83, 99, 122);
background-image: url("../images/handle_bg.svg");
background-repeat: no-repeat;
background-position: right;
box-shadow: 3px 3px 0px rgba(0, 0, 0, 0.5);
}
#noVNC_control_bar_handle:after {
content: "";
transition: transform 0.5s ease-in-out;
background: url("../images/handle.svg");
background-repeat: no-repeat;
background-position: center;
position: absolute;
top: 22px; /* (50px-6px)/2 */
right: 5px;
width: 5px;
height: 6px;
right: 0px;
width: 15px;
height: 60px;
background-color: rgb(9 2 2 / 0.6);
border-bottom-right-radius: 10px;
border-top-right-radius: 10px;
border-color: rgb(255 255 255 / 0.6);
border-style: inset;
}
#noVNC_control_bar.noVNC_open #noVNC_control_bar_handle:after {
transform: translateX(1px) rotate(180deg);
@ -431,6 +436,7 @@ select:active {
}
.noVNC_right #noVNC_control_bar_handle {
background-position: left;
}
.noVNC_right #noVNC_control_bar_handle:after {
left: 5px;
@ -495,18 +501,23 @@ select:active {
transform: translateY(-50%) scale(1);
}
.noVNC_button_div {
display: block;
color: #fff;
font-size: 13px;
}
/* General button style */
.noVNC_button {
display: block;
display: inline;
padding: 4px 4px;
margin: 10px 0;
vertical-align: middle;
border:1px solid rgba(255, 255, 255, 0.2);
border-radius: 6px;
}
.noVNC_button.noVNC_selected {
border-color: rgba(0, 0, 0, 0.8);
background: rgba(0, 0, 0, 0.5);
background: rgba(153, 151, 157, 0.68);
}
.noVNC_button:disabled {
opacity: 0.4;
@ -523,10 +534,10 @@ select:active {
:root:not(.noVNC_touch) .noVNC_button.noVNC_selected:hover,
.noVNC_button.noVNC_selected:focus {
border-color: rgba(0, 0, 0, 0.4);
background: rgba(0, 0, 0, 0.2);
background: rgba(153, 151, 157, 0.68);
}
:root:not(.noVNC_touch) .noVNC_button:hover,
.noVNC_button:focus {
:root:not(.noVNC_touch) .noVNC_button_div:hover,
.noVNC_button_div:focus {
background: rgba(255, 255, 255, 0.2);
}
.noVNC_button.noVNC_hidden {
@ -539,6 +550,7 @@ select:active {
transition: 0.5s ease-in-out;
width: 300px;
max-height: 100vh; /* Chrome is buggy with 100% */
overflow-x: hidden;
overflow-y: auto;
@ -548,11 +560,9 @@ select:active {
padding: 15px;
background: #fff;
background: rgb(9 9 0 / 0.77);
border-radius: 10px;
color: #000;
border: 2px solid #E0E0E0;
box-shadow: 6px 6px 0px rgba(0, 0, 0, 0.5);
}
.noVNC_panel.noVNC_open {
visibility: visible;
@ -578,10 +588,11 @@ select:active {
.noVNC_panel label {
display: block;
white-space: nowrap;
color:white;
}
.noVNC_panel .noVNC_heading {
background-color: rgb(110, 132, 163);
background-color: rgb(54,58,64);
border-radius: 5px;
padding: 5px;
/* Compensate for padding in image */
@ -602,12 +613,16 @@ select:active {
/* Expanders */
.noVNC_expander {
cursor: pointer;
color:white;
}
.noVNC_expander::before {
content: url("../images/expander.svg");
display: inline-block;
margin-right: 5px;
transition: 0.2s ease-in-out;
-webkit-filter: invert(.75); /* safari 6.0 - 9.0 */
filter: invert(.75);
}
.noVNC_expander.noVNC_open::before {
transform: rotateZ(90deg);
@ -630,6 +645,14 @@ select:active {
text-align: center;
}
:root:not(.noVNC_disconnected) .noVNC_hide_on_connect {
display: none
}
:root:not(.noVNC_connected) .noVNC_hide_on_disconnect {
display: none;
}
:root:not(.noVNC_connected) #noVNC_view_drag_button {
display: none;
}
@ -687,6 +710,7 @@ select:active {
list-style: none;
margin: 0px;
padding: 0px;
color:white;
}
#noVNC_setting_port {
width: 80px;
@ -776,81 +800,6 @@ select:active {
content: url("../images/warning.svg") " ";
}
/* ----------------------------------------
* Connect Dialog
* ----------------------------------------
*/
#noVNC_connect_dlg {
transition: 0.5s ease-in-out;
transform: scale(0, 0);
visibility: hidden;
opacity: 0;
}
#noVNC_connect_dlg.noVNC_open {
transform: scale(1, 1);
visibility: visible;
opacity: 1;
}
#noVNC_connect_dlg .noVNC_logo {
transition: 0.5s ease-in-out;
padding: 10px;
margin-bottom: 10px;
font-size: 80px;
text-align: center;
border-radius: 5px;
}
@media (max-width: 440px) {
#noVNC_connect_dlg {
max-width: calc(100vw - 100px);
}
#noVNC_connect_dlg .noVNC_logo {
font-size: calc(25vw - 30px);
}
}
#noVNC_connect_button {
cursor: pointer;
/*
padding: 10px;
color: white;
background-color: rgb(110, 132, 163);
border-radius: 12px;
box-shadow: 6px 6px 0px rgba(0, 0, 0, 0.5);
*/
text-align: center;
font-size: 20px;
margin-top: 130px;
}
#noVNC_connect_button div {
margin: 2px;
padding: 5px 30px;
border: 1px solid rgb(83, 99, 122);
border-bottom-width: 2px;
border-radius: 5px;
background: linear-gradient(to top, rgb(110, 132, 163), rgb(99, 119, 147));
/* This avoids it jumping around when :active */
vertical-align: middle;
color: white;
}
#noVNC_connect_button div:active {
border-bottom-width: 1px;
margin-top: 3px;
}
:root:not(.noVNC_touch) #noVNC_connect_button div:hover {
background: linear-gradient(to top, rgb(110, 132, 163), rgb(105, 125, 155));
}
#noVNC_connect_button img {
vertical-align: bottom;
height: 1.3em;
}
/* ----------------------------------------
* Password Dialog
@ -930,9 +879,7 @@ select:active {
#noVNC_container {
width: 100%;
height: 100%;
background-color: rgb(74, 144, 217, 0.5);
border-bottom-right-radius: 800px 600px;
/*border-top-left-radius: 800px 600px;*/
background-image: url('../images/splash.jpg')
}
#noVNC_keyboardinput {
@ -962,6 +909,10 @@ select:active {
font-family: 'Orbitron', 'OrbitronTTF', sans-serif;
line-height:90%;
text-shadow: 0.1em 0.1em 0 black;
margin-bottom: 0px;
}
.noVNC_logo img {
width: 45%
}
.noVNC_logo span{
color:green;
@ -1139,3 +1090,75 @@ body {
font-size: 90px;
}
}
/* ----------------------------------------
* Slider Check boxes
* ----------------------------------------
*/
/* The switch - the box around the slider */
.switch {
position: relative;
display: inline-block;
width: 30px;
height: 16px;
margin: 5px;
}
/* Hide default HTML checkbox */
.switch input {
opacity: 0;
width: 0;
height: 0;
}
/* The slider */
.slider {
position: absolute;
cursor: pointer;
top: 0;
left: 0;
right: 0;
bottom: 0;
background-color: #ccc;
-webkit-transition: .4s;
transition: .4s;
}
.slider:before {
position: absolute;
content: "";
height: 14px;
width: 14px;
left: 4px;
bottom: 1px;
background-color: white;
-webkit-transition: .4s;
transition: .4s;
}
input:checked + .slider {
background-color: #2196F3;
}
input:focus + .slider {
box-shadow: 0 0 1px #2196F3;
}
input:checked + .slider:before {
-webkit-transform: translateX(26px);
-ms-transform: translateX(26px);
transform: translateX(10px);
}
/* Rounded sliders */
.slider.round {
border-radius: 34px;
}
.slider.round:before {
border-radius: 50%;
}
.slider-label {
padding-left: 26px;
}

193
app/ui.js
View File

@ -128,6 +128,7 @@ const UI = {
UI.addControlbarHandlers();
UI.addTouchSpecificHandlers();
UI.addExtraKeysHandlers();
UI.addGamingHandlers();
UI.addMachineHandlers();
UI.addConnectionControlHandlers();
UI.addClipboardHandlers();
@ -146,8 +147,6 @@ const UI = {
UI.connect();
} else {
autoconnect = false;
// Show the connect panel on first load unless autoconnecting
UI.openConnectPanel();
}
window.parent.postMessage({
@ -178,8 +177,7 @@ const UI = {
document.documentElement.mozRequestFullScreen ||
document.documentElement.webkitRequestFullscreen ||
document.body.msRequestFullscreen)) {
document.getElementById('noVNC_fullscreen_button')
.classList.remove("noVNC_hidden");
UI.showControlInput("noVNC_fullscreen_button")
UI.addFullscreenHandlers();
}
},
@ -348,12 +346,7 @@ const UI = {
document.getElementById("noVNC_control_bar")
.addEventListener('keydown', UI.keepControlbar);
document.getElementById("noVNC_view_drag_button")
.addEventListener('click', UI.toggleViewDrag);
document
.getElementById("noVNC_setting_pointer_lock")
.addEventListener("click", UI.togglePointerLock);
UI.addClickHandle('noVNC_view_drag_button', UI.toggleViewDrag);
document.getElementById("noVNC_control_bar_handle")
.addEventListener('mousedown', UI.controlbarHandleMouseDown);
@ -406,8 +399,8 @@ const UI = {
},
addExtraKeysHandlers() {
document.getElementById("noVNC_toggle_extra_keys_button")
.addEventListener('click', UI.toggleExtraKeys);
UI.addClickHandle('noVNC_toggle_extra_keys_button', UI.toggleExtraKeys);
document.getElementById("noVNC_toggle_ctrl_button")
.addEventListener('click', UI.toggleCtrl);
document.getElementById("noVNC_toggle_windows_button")
@ -420,24 +413,29 @@ const UI = {
.addEventListener('click', UI.sendEsc);
document.getElementById("noVNC_send_ctrl_alt_del_button")
.addEventListener('click', UI.sendCtrlAltDel);
document.getElementById("noVNC_game_mode_button")
.addEventListener("click", UI.toggleRelativePointer)
},
addGamingHandlers() {
UI.addClickHandle('noVNC_game_mode_button', UI.toggleRelativePointer);
document
.getElementById("noVNC_setting_pointer_lock")
.addEventListener("click", UI.togglePointerLock);
},
addMachineHandlers() {
UI.addClickHandle('noVNC_power_button', UI.togglePowerPanel);
document.getElementById("noVNC_shutdown_button")
.addEventListener('click', () => UI.rfb.machineShutdown());
document.getElementById("noVNC_reboot_button")
.addEventListener('click', () => UI.rfb.machineReboot());
document.getElementById("noVNC_reset_button")
.addEventListener('click', () => UI.rfb.machineReset());
document.getElementById("noVNC_power_button")
.addEventListener('click', UI.togglePowerPanel);
},
addConnectionControlHandlers() {
document.getElementById("noVNC_disconnect_button")
.addEventListener('click', UI.disconnect);
UI.addClickHandle('noVNC_disconnect_button', UI.disconnect);
var connect_btn_el = document.getElementById("noVNC_connect_button");
if (typeof(connect_btn_el) != 'undefined' && connect_btn_el != null)
{
@ -451,8 +449,8 @@ const UI = {
},
addClipboardHandlers() {
document.getElementById("noVNC_clipboard_button")
.addEventListener('click', UI.toggleClipboardPanel);
UI.addClickHandle('noVNC_clipboard_button', UI.toggleClipboardPanel);
document.getElementById("noVNC_clipboard_text")
.addEventListener('change', UI.clipboardSend);
document.getElementById("noVNC_clipboard_clear_button")
@ -472,8 +470,7 @@ const UI = {
},
addSettingsHandlers() {
document.getElementById("noVNC_settings_button")
.addEventListener('click', UI.toggleSettingsPanel);
UI.addClickHandle('noVNC_settings_button', UI.toggleSettingsPanel);
document.getElementById("noVNC_setting_enable_perf_stats").addEventListener('click', UI.showStats);
@ -542,8 +539,7 @@ const UI = {
},
addFullscreenHandlers() {
document.getElementById("noVNC_fullscreen_button")
.addEventListener('click', UI.toggleFullscreen);
UI.addClickHandle('noVNC_fullscreen_button', UI.toggleFullscreen);
window.addEventListener('fullscreenchange', UI.updateFullscreenButton);
window.addEventListener('mozfullscreenchange', UI.updateFullscreenButton);
@ -556,6 +552,20 @@ const UI = {
* ==============
* VISUAL
* ------v------*/
// Ignore clicks that are propogated from child elements in sub panels
isControlPanelItemClick(e) {
if (!(e && e.target && e.target.classList && e.target.parentNode &&
(
e.target.classList.contains('noVNC_button') && e.target.parentNode.id !== 'noVNC_modifiers' ||
e.target.classList.contains('noVNC_button_div') ||
e.target.classList.contains('noVNC_heading')
)
)) {
return false;
}
return true;
},
// Disable/enable controls depending on connection state
updateVisualState(state) {
@ -564,6 +574,7 @@ const UI = {
document.documentElement.classList.remove("noVNC_connected");
document.documentElement.classList.remove("noVNC_disconnecting");
document.documentElement.classList.remove("noVNC_reconnecting");
document.documentElement.classList.remove("noVNC_disconnected");
const transitionElem = document.getElementById("noVNC_transition_text");
if (WebUtil.isInsideKasmVDI())
@ -586,6 +597,7 @@ const UI = {
document.documentElement.classList.add("noVNC_disconnecting");
break;
case 'disconnected':
document.documentElement.classList.add("noVNC_disconnected");
break;
case 'reconnecting':
transitionElem.textContent = _("Reconnecting...");
@ -746,7 +758,9 @@ const UI = {
UI.closeAllPanels();
document.getElementById('noVNC_control_bar')
.classList.remove("noVNC_open");
if (UI.rfb) {
UI.rfb.focus();
}
},
toggleControlbar() {
@ -919,6 +933,48 @@ const UI = {
}
},
addClickHandle(domElementName, funcToCall) {
/* Add click handler, will attach to parent if appropriate */
var control = document.getElementById(domElementName);
if (control.parentNode.classList.contains('noVNC_button_div')) {
control.parentNode.addEventListener('click', funcToCall);
} else {
control.addEventListener('click', funcToCall);
}
},
showControlInput(name) {
var control = document.getElementById(name);
/*var control_label = document.getElementById(name + '_label');
if (control) {
control.classList.remove("noVNC_hidden");
}
if (control_label) {
control_label.classList.remove("noVNC_hidden");
} */
if (control.parentNode.classList.contains('noVNC_button_div')) {
control.parentNode.classList.remove("noVNC_hidden")
} else {
control.classList.remove("noVNC_hidden")
}
},
hideControlInput(name) {
var control = document.getElementById(name);
/*var control_label = document.getElementById(name + '_label');
if (control) {
control.classList.add("noVNC_hidden");
}
if (control_label) {
control_label.classList.add("noVNC_hidden");
}*/
if (control.parentNode.classList.contains('noVNC_button_div')) {
control.parentNode.classList.add("noVNC_hidden")
} else {
control.classList.add("noVNC_hidden")
}
},
/* ------^-------
* /VISUAL
* ==============
@ -1085,7 +1141,11 @@ const UI = {
.classList.remove("noVNC_selected");
},
toggleSettingsPanel() {
toggleSettingsPanel(e) {
if (!UI.isControlPanelItemClick(e)) {
return false;
}
if (document.getElementById('noVNC_settings')
.classList.contains("noVNC_open")) {
UI.closeSettingsPanel();
@ -1117,7 +1177,11 @@ const UI = {
.classList.remove("noVNC_selected");
},
togglePowerPanel() {
togglePowerPanel(e) {
if (!UI.isControlPanelItemClick(e)) {
return false;
}
if (document.getElementById('noVNC_power')
.classList.contains("noVNC_open")) {
UI.closePowerPanel();
@ -1131,11 +1195,9 @@ const UI = {
if (UI.connected &&
UI.rfb.capabilities.power &&
!UI.rfb.viewOnly) {
document.getElementById('noVNC_power_button')
.classList.remove("noVNC_hidden");
UI.showControlInput('noVNC_power_button')
} else {
document.getElementById('noVNC_power_button')
.classList.add("noVNC_hidden");
UI.hideControlInput('noVNC_power_button');
// Close power panel if open
UI.closePowerPanel();
}
@ -1164,7 +1226,11 @@ const UI = {
.classList.remove("noVNC_selected");
},
toggleClipboardPanel() {
toggleClipboardPanel(e) {
if (!UI.isControlPanelItemClick(e)) {
return false;
}
if (document.getElementById('noVNC_clipboard')
.classList.contains("noVNC_open")) {
UI.closeClipboardPanel();
@ -1254,16 +1320,6 @@ const UI = {
* CONNECTION
* ------v------*/
openConnectPanel() {
document.getElementById('noVNC_connect_dlg')
.classList.add("noVNC_open");
},
closeConnectPanel() {
document.getElementById('noVNC_connect_dlg')
.classList.remove("noVNC_open");
},
connect(event, password) {
// Ignore when rfb already exists
@ -1292,8 +1348,6 @@ const UI = {
return;
}
UI.closeConnectPanel();
UI.updateVisualState('connecting');
let url;
@ -1383,7 +1437,6 @@ const UI = {
}
UI.rfb.addEventListener("disconnect", UI.disconnectedRx);
document.getElementById('noVNC_control_bar_anchor').setAttribute('style', 'display: none');
document.getElementById('noVNC_connect_dlg').innerHTML = '';
//keep alive for websocket connection to stay open, since we may not control reverse proxies
//send a keep alive within a window that we control
@ -1464,7 +1517,6 @@ const UI = {
UI.updateVisualState('disconnected');
UI.openControlbar();
UI.openConnectPanel();
},
connectFinished(e) {
@ -1518,7 +1570,6 @@ const UI = {
document.title = PAGE_TITLE;
UI.openControlbar();
UI.openConnectPanel();
if (UI.forceReconnect) {
UI.forceReconnect = false;
@ -1791,19 +1842,11 @@ const UI = {
(document.pointerLockElement !== undefined ||
document.mozPointerLockElement !== undefined)
) {
document
.getElementById("noVNC_setting_pointer_lock")
.classList.remove("noVNC_hidden");
document
.getElementById("noVNC_game_mode_button")
.classList.remove("noVNC_hidden");
UI.showControlInput("noVNC_setting_pointer_lock");
UI.showControlInput("noVNC_game_mode_button");
} else {
document
.getElementById("noVNC_setting_pointer_lock")
.classList.add("noVNC_hidden");
document
.getElementById("noVNC_game_mode_button")
.classList.add("noVNC_hidden");
UI.hideControlInput("noVNC_setting_pointer_lock");
UI.hideControlInput("noVNC_game_mode_button");
}
},
@ -1878,9 +1921,9 @@ const UI = {
}
if (UI.rfb.clipViewport) {
viewDragButton.classList.remove("noVNC_hidden");
UI.showControlInput('noVNC_view_drag_button');
} else {
viewDragButton.classList.add("noVNC_hidden");
UI.hideControlInput('noVNC_view_drag_button');
}
},
@ -2178,7 +2221,11 @@ const UI = {
.classList.remove("noVNC_selected");
},
toggleExtraKeys() {
toggleExtraKeys(e) {
if (!UI.isControlPanelItemClick(e)) {
return false;
}
if (document.getElementById('noVNC_modifiers').classList.contains("noVNC_open")) {
UI.closeExtraKeys();
} else {
@ -2272,23 +2319,15 @@ const UI = {
// Hide input related buttons in view only mode
if (UI.rfb.viewOnly) {
document.getElementById('noVNC_keyboard_button')
.classList.add('noVNC_hidden');
document.getElementById('noVNC_toggle_extra_keys_button')
.classList.add('noVNC_hidden');
document.getElementById('noVNC_clipboard_button')
.classList.add('noVNC_hidden');
document.getElementById('noVNC_game_mode_button')
.classList.add('noVNC_hidden');
UI.hideControlInput("noVNC_keyboard_button");
UI.hideControlInput("noVNC_toggle_extra_keys_button");
UI.hideControlInput("noVNC_clipboard_button");
UI.hideControlInput("noVNC_game_mode_button");
} else {
document.getElementById('noVNC_keyboard_button')
.classList.remove('noVNC_hidden');
document.getElementById('noVNC_toggle_extra_keys_button')
.classList.remove('noVNC_hidden');
document.getElementById('noVNC_clipboard_button')
.classList.remove('noVNC_hidden');
document.getElementById('noVNC_game_mode_button')
.classList.remove('noVNC_hidden');
UI.showControlInput("noVNC_keyboard_button");
UI.showControlInput("noVNC_toggle_extra_keys_button");
UI.showControlInput("noVNC_clipboard_button");
UI.showControlInput("noVNC_game_mode_button");
}
},

232
vnc.html
View File

@ -86,6 +86,31 @@
Loading statistics...
</div>
<!-- noVNC Control Bar -->
<div id="noVNC_control_bar_anchor" class="noVNC_vcenter">
<div id="noVNC_control_bar">
<div id="noVNC_control_bar_handle" title="Hide/Show the control bar">
<div></div>
</div>
<div class="noVNC_scroll">
<h1 class="noVNC_logo"><img src="app/images/icons/kasm_logo.png" /></h1>
<!-- Drag/Pan the viewport -->
<div class="noVNC_button_div noVNC_hidden noVNC_hide_on_disconnect" >
<input type="image" alt="Drag" src="app/images/drag.svg"
id="noVNC_view_drag_button" class="noVNC_button"
title="Move/Drag Viewport">
Drag Viewport
</div>
<!--noVNC Touch Device only buttons-->
<!-- Extra manual keys -->
<div class="noVNC_button_div noVNC_hide_on_disconnect" >
<input type="image" alt="Extra keys" src="app/images/toggleextrakeys.svg"
id="noVNC_toggle_extra_keys_button" class="noVNC_button"
title="Show Extra Keys">
<div class="noVNC_vcenter">
<div id="noVNC_modifiers" class="noVNC_panel">
<input type="image" alt="Keyboard" src="app/images/keyboard.svg"
@ -110,32 +135,15 @@
title="Send Ctrl-Alt-Del">
</div>
</div>
<!-- noVNC Control Bar -->
<div id="noVNC_control_bar_anchor" class="noVNC_vcenter">
<div id="noVNC_control_bar">
<div id="noVNC_control_bar_handle" title="Hide/Show the control bar"><div></div></div>
<div class="noVNC_scroll">
<h1 class="noVNC_logo"><img src="app/images/icons/368_kasm_logo_only_24x24.png" /></h1>
<!-- Drag/Pan the viewport -->
<input type="image" alt="Drag" src="app/images/drag.svg"
id="noVNC_view_drag_button" class="noVNC_button noVNC_hidden"
title="Move/Drag Viewport">
<!--noVNC Touch Device only buttons-->
<!-- Extra manual keys -->
<input type="image" alt="Extra keys" src="app/images/toggleextrakeys.svg"
id="noVNC_toggle_extra_keys_button" class="noVNC_button"
title="Show Extra Keys">
Keys
</div>
<!-- Shutdown/Reboot -->
<div class="noVNC_button_div noVNC_hide_on_disconnect" >
<input type="image" alt="Shutdown/Reboot" src="app/images/power.svg"
id="noVNC_power_button" class="noVNC_button"
title="Shutdown/Reboot...">
<div class="noVNC_vcenter">
<div id="noVNC_power" class="noVNC_panel">
<div class="noVNC_heading">
@ -146,11 +154,15 @@
<input type="button" id="noVNC_reset_button" value="Reset">
</div>
</div>
Power
</div>
<!-- Clipboard -->
<div class="noVNC_button_div noVNC_hide_on_disconnect" >
<input type="image" alt="Clipboard" src="app/images/clipboard.svg"
id="noVNC_clipboard_button" class="noVNC_button"
title="Clipboard">
Clipboard
<div class="noVNC_vcenter">
<div id="noVNC_clipboard" class="noVNC_panel">
<div class="noVNC_heading">
@ -162,18 +174,26 @@
value="Clear" class="noVNC_submit">
</div>
</div>
</div>
<!-- Toggle fullscreen -->
<div class="noVNC_button_div noVNC_hidden" >
<input type="image" alt="Fullscreen" src="app/images/fullscreen.svg"
id="noVNC_fullscreen_button" class="noVNC_button noVNC_hidden"
id="noVNC_fullscreen_button" class="noVNC_button"
title="Fullscreen">
Fullscreen
</div>
<!-- Toggle game mode -->
<div class="noVNC_button_div noVNC_hidden noVNC_hide_on_disconnect" >
<input type="image" alt="Game Mode" src="app/images/gamepad.png"
id="noVNC_game_mode_button" class="noVNC_button noVNC_hidden"
id="noVNC_game_mode_button" class="noVNC_button"
title="Game Pointer Mode">
Game Cursor Mode
</div>
<!-- Settings -->
<div class="noVNC_button_div" >
<input type="image" alt="Settings" src="app/images/settings.svg"
id="noVNC_settings_button" class="noVNC_button"
title="Settings">
@ -184,47 +204,101 @@
<img alt="" src="app/images/settings.svg"> Settings
</li>
<li>
<label><input id="noVNC_setting_shared" type="checkbox"> Shared Mode</label>
</li>
<li>
<label><input id="noVNC_setting_view_only" type="checkbox" /> View Only</label></li>
<li>
<label><input id="noVNC_setting_clipboard_up" type="checkbox" /> Clipboard Up</label></li>
<li>
<label><input id="noVNC_setting_clipboard_down" type="checkbox" /> Clipboard Down</label></li>
<li>
<label><input id="noVNC_setting_clipboard_seamless" type="checkbox" /> Clipboard Seamless</label></li>
<li>
<label><input id="noVNC_setting_prefer_local_cursor" type="checkbox" /> Prefer Local Cursor</label>
</li>
<li>
<label>
<input id="noVNC_setting_translate_shortcuts" type="checkbox" />Translate keyboard shurtcuts
<label class="switch"><input id="noVNC_setting_shared" type="checkbox">
<span class="slider round"></span>
<span class="slider-label">Shared Mode</span>
</label>
</li>
<li>
<label><input id="noVNC_setting_enable_webp" type="checkbox" /> Enable WebP Compression</label></li>
<li>
<label><input id="noVNC_setting_enable_perf_stats" type="checkbox" /> Enable Performance Stats</label></li>
<li>
<label>
<input type="checkbox" id="noVNC_setting_pointer_lock" /> Enable Pointer Lock
<label class="switch"><input id="noVNC_setting_view_only" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">View Only</span>
</label>
</li>
<label><input id="noVNC_setting_enable_ime" type="checkbox" /> IME Input Mode</label></li>
<li>
<label><input id="noVNC_setting_virtual_keyboard_visible" type="checkbox" /> Show Virtual Keyboard Control</label></li>
<label class="switch"><input id="noVNC_setting_clipboard_up" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Clipboard Up</span>
</label>
</li>
<li>
<label><input id="noVNC_setting_toggle_control_panel" type="checkbox" /> Toggle Control Panel via Keystrokes</label></li>
<label class="switch"><input id="noVNC_setting_clipboard_down" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Clipboard Down</span>
</label>
</li>
<li>
<label class="switch"><input id="noVNC_setting_clipboard_seamless" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Clipboard Seamless</span>
</label>
</li>
<li>
<label class="switch"><input id="noVNC_setting_prefer_local_cursor" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Prefer Local Cursor</span>
</label>
</li>
<li>
<label class="switch">
<input id="noVNC_setting_translate_shortcuts" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Translate keyboard shurtcuts</span>
</label>
</li>
<li>
<label class="switch"><input id="noVNC_setting_enable_webp" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Enable WebP Compression</span>
</label>
</li>
<li>
<label class="switch">
<input id="noVNC_setting_enable_perf_stats" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Enable Performance Stats</span>
</label>
</li>
<li>
<label class="switch">
<input type="checkbox" id="noVNC_setting_pointer_lock" />
<span class="slider round"></span>
<span class="slider-label">Enable Pointer Lock</span>
</label>
</li>
<label class="switch"><input id="noVNC_setting_enable_ime" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">IME Input Mode</span>
</label>
</li>
<li>
<label class="switch"><input id="noVNC_setting_virtual_keyboard_visible" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Show Virtual Keyboard Control</span>
</label>
</li>
<li>
<label class="switch"><input id="noVNC_setting_toggle_control_panel" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Toggle Control Panel via Keystrokes</span>
</label>
</li>
<li>
<label for="noVNC_setting_idle_disconnect">Idle Timeout:</label>
<select id="noVNC_setting_idle_disconnect" name="vncIdleDisconnect">
<option value=10>10</option>
<option value=20>20</option>
<option value=30>30</option>
<option value=60>60</option>
</select>
</li>
<li><hr></li>
<li>
<label><input id="noVNC_setting_view_clip" type="checkbox"> Clip to Window</label>
<label class="switch">
<input id="noVNC_setting_view_clip" type="checkbox">
<span class="slider round"></span>
<span class="slider-label">Clip to Window</span>
</label>
</li>
<li>
<label for="noVNC_setting_resize">Scaling Mode:</label>
@ -240,8 +314,10 @@
<div>
<ul>
<li>
<label>
<input id="noVNC_setting_toggle_control_panel" type="checkbox" /> Enable KasmVNC Keyboard Shortcuts
<label class="switch">
<input id="noVNC_setting_toggle_control_panel" type="checkbox" />
<span class="slider round"></span>
<span class="slider-label">Enable KasmVNC Keyboard Shortcuts</span>
</label>
</li>
<li>Ctrl+Shift+</li>
@ -254,7 +330,8 @@
<li><hr></li>
<li>
<div class="noVNC_expander">Stream Quality</div>
<div><ul>
<div>
<ul>
<li>
<label for="noVNC_setting_video_quality">Preset Modes:</label>
<select id="noVNC_setting_video_quality" name="vncVideoQuality">
@ -339,12 +416,14 @@
<label for="noVNC_setting_max_video_resolution_y">Video Mode Height:</label>
<input id="noVNC_setting_max_video_resolution_y" type="number" min="100" max="2160" value="540">
</li>
</ul></div>
</ul>
</div>
</li>
<li><hr></li>
<li>
<div class="noVNC_expander">Advanced</div>
<div><ul>
<div>
<ul>
<li>
<label for="noVNC_setting_compression">Compression level:</label>
<input id="noVNC_setting_compression" type="range" min="0" max="9" value="2">
@ -356,9 +435,14 @@
</li>
<li>
<div class="noVNC_expander">WebSocket</div>
<div><ul>
<div>
<ul>
<li>
<label><input id="noVNC_setting_encrypt" type="checkbox"> Encrypt</label>
<label class="switch">
<input id="noVNC_setting_encrypt" type="checkbox">
<span class="slider round"></span>
<span class="slider-label">Encrypt</span>
</label>
</li>
<li>
<label for="noVNC_setting_host">Host:</label>
@ -372,11 +456,15 @@
<label for="noVNC_setting_path">Path:</label>
<input id="noVNC_setting_path" type="text" value="websockify">
</li>
</ul></div>
</ul>
</div>
</li>
<li><hr></li>
<li>
<label><input id="noVNC_setting_reconnect" type="checkbox"> Automatic Reconnect</label>
<label class="switch">
<input id="noVNC_setting_reconnect" type="checkbox">
<span class="slider-label">Automatic Reconnect</span>
</label>
</li>
<li>
<label for="noVNC_setting_reconnect_delay">Reconnect Delay (ms):</label>
@ -384,7 +472,10 @@
</li>
<li><hr></li>
<li>
<label><input id="noVNC_setting_show_dot" type="checkbox"> Show Dot when No Cursor</label>
<label class="switch"><input id="noVNC_setting_show_dot" type="checkbox">
<span class="slider round"></span>
<span class="slider-label">Show Dot when No Cursor</span>
</label>
</li>
<li><hr></li>
<!-- Logging selection dropdown -->
@ -394,7 +485,8 @@
</select>
</label>
</li>
</ul></div>
</ul>
</div>
</li>
<li class="noVNC_version_separator"><hr></li>
<li class="noVNC_version_wrapper">
@ -404,11 +496,24 @@
</ul>
</div>
</div>
Settings
</div>
<!-- Connection Controls -->
<div class="noVNC_button_div noVNC_hide_on_disconnect" >
<input type="image" alt="Disconnect" src="app/images/disconnect.svg"
id="noVNC_disconnect_button" class="noVNC_button"
title="Disconnect">
Disconnect
</div>
<!-- Connection Controls -->
<div class="noVNC_button_div noVNC_hide_on_connect" id="noVNC_connect_button" >
<input type="image" alt="Connect" src="app/images/connect.svg"
class="noVNC_button"
title="Connect">
Connect
</div>
</div>
</div>
@ -423,10 +528,11 @@
<!-- Connect button -->
<div class="noVNC_center">
<div id="noVNC_connect_dlg">
<!--div class="noVNC_logo" translate="no"><span>no</span>VNC</div-->
<div id="noVNC_connect_button"><div>
<!--div id="noVNC_connect_button">
<div>
<img alt="" src="app/images/connect.svg"> Connect
</div></div>
</div>
</div-->
</div>
</div>