Decouple it from XVP and make it a generic API.
padding: 0 10px;
}
-/* XVP Shutdown/Reboot */
-:root:not(.noVNC_connected) #noVNC_xvp_button {
+/* Shutdown/Reboot */
+:root:not(.noVNC_connected) #noVNC_power_button {
display: none;
}
-#noVNC_xvp {
+#noVNC_power {
}
-#noVNC_xvp_buttons {
+#noVNC_power_buttons {
display: none;
}
-#noVNC_xvp input[type=button] {
+#noVNC_power input[type=button] {
width: 100%;
}
UI.addControlbarHandlers();
UI.addTouchSpecificHandlers();
UI.addExtraKeysHandlers();
- UI.addXvpHandlers();
+ UI.addMachineHandlers();
UI.addConnectionControlHandlers();
UI.addClipboardHandlers();
UI.addSettingsHandlers();
'onUpdateState': UI.updateState,
'onDisconnected': UI.disconnectFinished,
'onCredentialsRequired': UI.credentials,
- 'onXvpInit': UI.updateXvpButton,
+ 'onCapabilities': UI.updatePowerButton,
'onClipboard': UI.clipboardReceive,
'onBell': UI.bell,
'onFBUComplete': UI.initialResize,
.addEventListener('click', UI.sendCtrlAltDel);
},
- addXvpHandlers: function() {
- document.getElementById("noVNC_xvp_shutdown_button")
- .addEventListener('click', function() { UI.rfb.xvpShutdown(); });
- document.getElementById("noVNC_xvp_reboot_button")
- .addEventListener('click', function() { UI.rfb.xvpReboot(); });
- document.getElementById("noVNC_xvp_reset_button")
- .addEventListener('click', function() { UI.rfb.xvpReset(); });
- document.getElementById("noVNC_xvp_button")
- .addEventListener('click', UI.toggleXvpPanel);
+ addMachineHandlers: function() {
+ document.getElementById("noVNC_shutdown_button")
+ .addEventListener('click', function() { UI.rfb.machineShutdown(); });
+ document.getElementById("noVNC_reboot_button")
+ .addEventListener('click', function() { UI.rfb.machineReboot(); });
+ document.getElementById("noVNC_reset_button")
+ .addEventListener('click', function() { UI.rfb.machineReset(); });
+ document.getElementById("noVNC_power_button")
+ .addEventListener('click', UI.togglePowerPanel);
},
addConnectionControlHandlers: function() {
UI.enableSetting('port');
UI.enableSetting('path');
UI.enableSetting('repeaterID');
- UI.updateXvpButton(0);
+ UI.updatePowerButton();
UI.keepControlbar();
}
closeAllPanels: function() {
UI.closeSettingsPanel();
- UI.closeXvpPanel();
+ UI.closePowerPanel();
UI.closeClipboardPanel();
UI.closeExtraKeys();
},
/* ------^-------
* /SETTINGS
* ==============
- * XVP
+ * POWER
* ------v------*/
- openXvpPanel: function() {
+ openPowerPanel: function() {
UI.closeAllPanels();
UI.openControlbar();
- document.getElementById('noVNC_xvp')
+ document.getElementById('noVNC_power')
.classList.add("noVNC_open");
- document.getElementById('noVNC_xvp_button')
+ document.getElementById('noVNC_power_button')
.classList.add("noVNC_selected");
},
- closeXvpPanel: function() {
- document.getElementById('noVNC_xvp')
+ closePowerPanel: function() {
+ document.getElementById('noVNC_power')
.classList.remove("noVNC_open");
- document.getElementById('noVNC_xvp_button')
+ document.getElementById('noVNC_power_button')
.classList.remove("noVNC_selected");
},
- toggleXvpPanel: function() {
- if (document.getElementById('noVNC_xvp')
+ togglePowerPanel: function() {
+ if (document.getElementById('noVNC_power')
.classList.contains("noVNC_open")) {
- UI.closeXvpPanel();
+ UI.closePowerPanel();
} else {
- UI.openXvpPanel();
+ UI.openPowerPanel();
}
},
- // Disable/enable XVP button
- updateXvpButton: function(ver) {
- if (ver >= 1 && !UI.rfb.get_view_only()) {
- document.getElementById('noVNC_xvp_button')
+ // Disable/enable power button
+ updatePowerButton: function() {
+ if (UI.connected &&
+ UI.rfb.get_capabilities().power &&
+ !UI.rfb.get_view_only()) {
+ document.getElementById('noVNC_power_button')
.classList.remove("noVNC_hidden");
} else {
- document.getElementById('noVNC_xvp_button')
+ document.getElementById('noVNC_power_button')
.classList.add("noVNC_hidden");
- // Close XVP panel if open
- UI.closeXvpPanel();
+ // Close power panel if open
+ UI.closePowerPanel();
}
},
/* ------^-------
- * /XVP
+ * /POWER
* ==============
* CLIPBOARD
* ------v------*/
this._rfb_tightvnc = false;
this._rfb_xvp_ver = 0;
+ this._capabilities = { power: false };
+
this._encHandlers = {};
this._encStats = {};
'onFBUComplete': function () { }, // onFBUComplete(rfb): RFB FBU received and processed
'onFBResize': function () { }, // onFBResize(rfb, width, height): frame buffer resized
'onDesktopName': function () { }, // onDesktopName(rfb, name): desktop name received
- 'onXvpInit': function () { } // onXvpInit(version): XVP extensions active for this connection
+ 'onCapabilities': function () { } // onCapabilities(rfb, caps): the supported capabilities has changed
});
// main setup
return true;
},
- xvpOp: function (ver, op) {
- if (this._rfb_xvp_ver < ver) { return false; }
- Log.Info("Sending XVP operation " + op + " (version " + ver + ")");
- RFB.messages.xvpOp(this._sock, ver, op);
- return true;
- },
-
- xvpShutdown: function () {
- return this.xvpOp(1, 2);
+ machineShutdown: function () {
+ this._xvpOp(1, 2);
},
- xvpReboot: function () {
- return this.xvpOp(1, 3);
+ machineReboot: function () {
+ this._xvpOp(1, 3);
},
- xvpReset: function () {
- return this.xvpOp(1, 4);
+ machineReset: function () {
+ this._xvpOp(1, 4);
},
// Send a key press. If 'down' is not specified then send a down key
case 1: // XVP_INIT
this._rfb_xvp_ver = xvp_ver;
Log.Info("XVP extensions enabled (version " + this._rfb_xvp_ver + ")");
- this._onXvpInit(this._rfb_xvp_ver);
+ this._capabilities.power = true;
+ this._onCapabilities(this, this._capabilities)
break;
default:
this._fail("Unexpected server message",
this._timing.fbu_rt_start = (new Date()).getTime();
this._updateContinuousUpdates();
- }
+ },
+
+ _xvpOp: function (ver, op) {
+ if (this._rfb_xvp_ver < ver) { return; }
+ Log.Info("Sending XVP operation " + op + " (version " + ver + ")");
+ RFB.messages.xvpOp(this._sock, ver, op);
+ },
};
make_properties(RFB, [
['wsProtocols', 'rw', 'arr'], // Protocols to use in the WebSocket connection
['repeaterID', 'rw', 'str'], // [UltraVNC] RepeaterID to connect to
['viewportDrag', 'rw', 'bool'], // Move the viewport on mouse drags
+ ['capabilities', 'ro', 'arr'], // Supported capabilities
// Callback functions
['onUpdateState', 'rw', 'func'], // onUpdateState(rfb, state, oldstate): connection state change
['onFBUComplete', 'rw', 'func'], // onFBUComplete(rfb, fbu): RFB FBU received and processed
['onFBResize', 'rw', 'func'], // onFBResize(rfb, width, height): frame buffer resized
['onDesktopName', 'rw', 'func'], // onDesktopName(rfb, name): desktop name received
- ['onXvpInit', 'rw', 'func'] // onXvpInit(version): XVP extensions active for this connection
+ ['onCapabilities', 'rw', 'func'] // onCapabilities(rfb, caps): the supported capabilities has changed
]);
RFB.prototype.set_local_cursor = function (cursor) {
| wsProtocols | arr | RW | ['binary'] | Protocols to use in the WebSocket connection
| repeaterID | str | RW | '' | UltraVNC RepeaterID to connect to
| viewportDrag | bool | RW | false | Move the viewport on mouse drags
+| capabilities | arr | RO | [] | Supported capabilities (can include: 'power')
## 2 Methods
| disconnect | () | Disconnect
| sendCredentials | (credentials) | Send credentials after onCredentialsRequired callback
| sendCtrlAltDel | () | Send Ctrl-Alt-Del key sequence
-| xvpOp | (ver, op) | Send a XVP operation (2=shutdown, 3=reboot, 4=reset)
-| xvpShutdown | () | Send XVP shutdown.
-| xvpReboot | () | Send XVP reboot.
-| xvpReset | () | Send XVP reset.
+| machineShutdown | () | Request a shutdown of the remote machine.
+| machineReboot | () | Request a reboot of the remote machine.
+| machineReset | () | Request a reset of the remote machine.
| sendKey | (keysym, code, down) | Send a key press event. If down not specified, send a down and up event.
| clipboardPasteFrom | (text) | Send a clipboard paste event
| autoscale | (width, height, downscaleOnly) | Scale the display
| onFBUComplete | (rfb, fbu) | RFB FBU received and processed (see details below)
| onFBResize | (rfb, width, height) | Frame buffer (remote desktop) size changed
| onDesktopName | (rfb, name) | VNC desktop name recieved
-| onXvpInit | (version) | XVP extensions active for this connection.
+| onCapabilities | (rfb, capabilities) | The supported capabilities has changed
__RFB onUpdateState callback details__
client._rfb_xvp_ver = 1;
});
- it('should send the shutdown signal on #xvpShutdown', function () {
- client.xvpShutdown();
+ it('should send the shutdown signal on #machineShutdown', function () {
+ client.machineShutdown();
expect(client._sock).to.have.sent(new Uint8Array([0xFA, 0x00, 0x01, 0x02]));
});
- it('should send the reboot signal on #xvpReboot', function () {
- client.xvpReboot();
+ it('should send the reboot signal on #machineReboot', function () {
+ client.machineReboot();
expect(client._sock).to.have.sent(new Uint8Array([0xFA, 0x00, 0x01, 0x03]));
});
- it('should send the reset signal on #xvpReset', function () {
- client.xvpReset();
+ it('should send the reset signal on #machineReset', function () {
+ client.machineReset();
expect(client._sock).to.have.sent(new Uint8Array([0xFA, 0x00, 0x01, 0x04]));
});
- it('should support sending arbitrary XVP operations via #xvpOp', function () {
- client.xvpOp(1, 7);
- expect(client._sock).to.have.sent(new Uint8Array([0xFA, 0x00, 0x01, 0x07]));
- });
-
it('should not send XVP operations with higher versions than we support', function () {
- expect(client.xvpOp(2, 7)).to.be.false;
+ client._xvpOp(2, 7);
expect(client._sock.flush).to.not.have.been.called;
});
});
});
it('should set the XVP version and fire the callback with the version on XVP_INIT', function () {
- client.set_onXvpInit(sinon.spy());
+ client.set_onCapabilities(sinon.spy());
client._sock._websocket._receive_data(new Uint8Array([250, 0, 10, 1]));
expect(client._rfb_xvp_ver).to.equal(10);
- expect(client.get_onXvpInit()).to.have.been.calledOnce;
- expect(client.get_onXvpInit()).to.have.been.calledWith(10);
+ expect(client.get_onCapabilities()).to.have.been.calledOnce;
+ expect(client.get_onCapabilities()).to.have.been.calledWith(client, { power: true });
});
it('should fail on unknown XVP message types', function () {
</div>
</div>
- <!-- XVP Shutdown/Reboot -->
+ <!-- Shutdown/Reboot -->
<input type="image" alt="Shutdown/Reboot" src="app/images/power.svg"
- id="noVNC_xvp_button" class="noVNC_button"
+ id="noVNC_power_button" class="noVNC_button"
title="Shutdown/Reboot..." />
<div class="noVNC_vcenter">
- <div id="noVNC_xvp" class="noVNC_panel">
+ <div id="noVNC_power" class="noVNC_panel">
<div class="noVNC_heading">
<img src="app/images/power.svg"> Power
</div>
- <input type="button" id="noVNC_xvp_shutdown_button" value="Shutdown" />
- <input type="button" id="noVNC_xvp_reboot_button" value="Reboot" />
- <input type="button" id="noVNC_xvp_reset_button" value="Reset" />
+ <input type="button" id="noVNC_shutdown_button" value="Shutdown" />
+ <input type="button" id="noVNC_reboot_button" value="Reboot" />
+ <input type="button" id="noVNC_reset_button" value="Reset" />
</div>
</div>
rfb.sendCtrlAltDel();
return false;
}
- function xvpShutdown() {
- rfb.xvpShutdown();
+ function machineShutdown() {
+ rfb.machineShutdown();
return false;
}
- function xvpReboot() {
- rfb.xvpReboot();
+ function machineReboot() {
+ rfb.machineReboot();
return false;
}
- function xvpReset() {
- rfb.xvpReset();
+ function machineReset() {
+ rfb.machineReset();
return false;
}
function status(text, level) {
cad.disabled = false;
} else {
cad.disabled = true;
- xvpInit(0);
+ updatePowerButtons();
}
}
}, 500);
};
- function xvpInit(ver) {
- var xvpbuttons;
- xvpbuttons = document.getElementById('noVNC_xvp_buttons');
- if (ver >= 1) {
- xvpbuttons.style.display = 'inline';
+ function updatePowerButtons() {
+ var powerbuttons;
+ powerbuttons = document.getElementById('noVNC_power_buttons');
+ if (rfb.get_capabilities().power) {
+ powerbuttons.style.display = 'inline';
} else {
- xvpbuttons.style.display = 'none';
+ powerbuttons.style.display = 'none';
}
}
document.getElementById('sendCtrlAltDelButton').style.display = "inline";
document.getElementById('sendCtrlAltDelButton').onclick = sendCtrlAltDel;
- document.getElementById('xvpShutdownButton').onclick = xvpShutdown;
- document.getElementById('xvpRebootButton').onclick = xvpReboot;
- document.getElementById('xvpResetButton').onclick = xvpReset;
+ document.getElementById('machineShutdownButton').onclick = machineShutdown;
+ document.getElementById('machineRebootButton').onclick = machineReboot;
+ document.getElementById('machineResetButton').onclick = machineReset;
WebUtil.init_logging(WebUtil.getConfigVar('logging', 'warn'));
document.title = WebUtil.getConfigVar('title', 'noVNC');
'onNotification': notification,
'onUpdateState': updateState,
'onDisconnected': disconnected,
- 'onXvpInit': xvpInit,
+ 'onCapabilities': updatePowerButtons,
'onCredentialsRequired': credentials,
'onFBUComplete': FBUComplete,
'onDesktopName': updateDesktopName});
<td width="1%"><div id="noVNC_buttons">
<input type=button value="Send CtrlAltDel"
id="sendCtrlAltDelButton">
- <span id="noVNC_xvp_buttons">
+ <span id="noVNC_power_buttons">
<input type=button value="Shutdown"
- id="xvpShutdownButton">
+ id="machineShutdownButton">
<input type=button value="Reboot"
- id="xvpRebootButton">
+ id="machineRebootButton">
<input type=button value="Reset"
- id="xvpResetButton">
+ id="machineResetButton">
</span>
</div></td>
</tr></table>