]>
git.proxmox.com Git - mirror_novnc.git/blob - include/web-socket-js/web_socket.js
69053a114a1fd5e0ece2c1f3f822a41da9549872
1 // Copyright: Hiroshi Ichikawa <http://gimite.net/en/>
2 // Lincense: New BSD Lincense
3 // Reference: http://dev.w3.org/html5/websockets/
4 // Reference: http://tools.ietf.org/html/draft-hixie-thewebsocketprotocol
8 if (window
.WebSocket
) return;
10 var console
= window
.console
;
11 if (!console
) console
= {log: function(){ }, error: function(){ }};
14 if ('navigator' in window
&& 'plugins' in navigator
&& navigator
.plugins
['Shockwave Flash']) {
15 return !!navigator
.plugins
['Shockwave Flash'].description
;
17 if ('ActiveXObject' in window
) {
19 return !!new ActiveXObject('ShockwaveFlash.ShockwaveFlash').GetVariable('$version');
26 console
.error("Flash Player is not installed.");
30 WebSocket = function(url
, protocol
, proxyHost
, proxyPort
, headers
) {
32 self
.readyState
= WebSocket
.CONNECTING
;
33 self
.bufferedAmount
= 0;
34 WebSocket
.__addTask(function() {
36 WebSocket
.__flash
.create(url
, protocol
, proxyHost
|| null, proxyPort
|| 0, headers
|| null);
38 self
.__flash
.addEventListener("open", function(fe
) {
40 if (self
.onopen
) self
.onopen();
42 console
.error(e
.toString());
46 self
.__flash
.addEventListener("close", function(fe
) {
48 if (self
.onclose
) self
.onclose();
50 console
.error(e
.toString());
54 self
.__flash
.addEventListener("message", function(fe
) {
55 var data
= decodeURIComponent(fe
.getData());
59 if (window
.MessageEvent
) {
60 e
= document
.createEvent("MessageEvent");
61 e
.initMessageEvent("message", false, false, data
, null, null, window
);
68 console
.error(e
.toString());
72 self
.__flash
.addEventListener("stateChange", function(fe
) {
74 self
.readyState
= fe
.getReadyState();
75 self
.bufferedAmount
= fe
.getBufferedAmount();
77 console
.error(e
.toString());
81 //console.log("[WebSocket] Flash object is ready");
85 WebSocket
.prototype.send = function(data
) {
86 if (!this.__flash
|| this.readyState
== WebSocket
.CONNECTING
) {
87 throw "INVALID_STATE_ERR: Web Socket connection has not been established";
89 var result
= this.__flash
.send(data
);
90 if (result
< 0) { // success
93 this.bufferedAmount
= result
;
98 WebSocket
.prototype.close = function() {
99 if (!this.__flash
) return;
100 if (this.readyState
!= WebSocket
.OPEN
) return;
101 this.__flash
.close();
102 // Sets/calls them manually here because Flash WebSocketConnection.close cannot fire events
103 // which causes weird error:
104 // > You are trying to call recursively into the Flash Player which is not allowed.
105 this.readyState
= WebSocket
.CLOSED
;
106 if (this.onclose
) this.onclose();
110 * Implementation of {@link <a href="http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-registration">DOM 2 EventTarget Interface</a>}
112 * @param {string} type
113 * @param {function} listener
114 * @param {boolean} useCapture !NB Not implemented yet
117 WebSocket
.prototype.addEventListener = function(type
, listener
, useCapture
) {
118 if (!('__events' in this)) {
121 if (!(type
in this.__events
)) {
122 this.__events
[type
] = [];
123 if ('function' == typeof this['on' + type
]) {
124 this.__events
[type
].defaultHandler
= this['on' + type
];
125 this['on' + type
] = WebSocket_FireEvent(this, type
);
128 this.__events
[type
].push(listener
);
132 * Implementation of {@link <a href="http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-registration">DOM 2 EventTarget Interface</a>}
134 * @param {string} type
135 * @param {function} listener
136 * @param {boolean} useCapture NB! Not implemented yet
139 WebSocket
.prototype.removeEventListener = function(type
, listener
, useCapture
) {
140 if (!('__events' in this)) {
143 if (!(type
in this.__events
)) return;
144 for (var i
= this.__events
.length
; i
> -1; --i
) {
145 if (listener
=== this.__events
[type
][i
]) {
146 this.__events
[type
].splice(i
, 1);
153 * Implementation of {@link <a href="http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-registration">DOM 2 EventTarget Interface</a>}
155 * @param {WebSocketEvent} event
158 WebSocket
.prototype.dispatchEvent = function(event
) {
159 if (!('__events' in this)) throw 'UNSPECIFIED_EVENT_TYPE_ERR';
160 if (!(event
.type
in this.__events
)) throw 'UNSPECIFIED_EVENT_TYPE_ERR';
162 for (var i
= 0, l
= this.__events
[event
.type
].length
; i
< l
; ++ i
) {
163 this.__events
[event
.type
][i
](event
);
164 if (event
.cancelBubble
) break;
167 if (false !== event
.returnValue
&&
168 'function' == typeof this.__events
[event
.type
].defaultHandler
)
170 this.__events
[event
.type
].defaultHandler(event
);
176 * @param {object} object
177 * @param {string} type
179 function WebSocket_FireEvent(object
, type
) {
180 return function(data
) {
181 var event
= new WebSocketEvent();
182 event
.initEvent(type
, true, true);
183 event
.target
= event
.currentTarget
= object
;
184 for (var key
in data
) {
185 event
[key
] = data
[key
];
187 object
.dispatchEvent(event
, arguments
);
192 * Basic implementation of {@link <a href="http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-interface">DOM 2 EventInterface</a>}
197 function WebSocketEvent(){}
203 WebSocketEvent
.prototype.cancelable
= true;
209 WebSocketEvent
.prototype.cancelBubble
= false;
215 WebSocketEvent
.prototype.preventDefault = function() {
216 if (this.cancelable
) {
217 this.returnValue
= false;
225 WebSocketEvent
.prototype.stopPropagation = function() {
226 this.cancelBubble
= true;
231 * @param {string} eventTypeArg
232 * @param {boolean} canBubbleArg
233 * @param {boolean} cancelableArg
236 WebSocketEvent
.prototype.initEvent = function(eventTypeArg
, canBubbleArg
, cancelableArg
) {
237 this.type
= eventTypeArg
;
238 this.cancelable
= cancelableArg
;
239 this.timeStamp
= new Date();
243 WebSocket
.CONNECTING
= 0;
245 WebSocket
.CLOSED
= 2;
247 WebSocket
.__tasks
= [];
249 WebSocket
.__initialize = function() {
250 if (!WebSocket
.__swfLocation
) {
251 console
.error("[WebSocket] set WebSocket.__swfLocation to location of WebSocketMain.swf");
254 var container
= document
.createElement("div");
255 container
.id
= "webSocketContainer";
256 // Puts the Flash out of the window. Note that we cannot use display: none or visibility: hidden
257 // here because it prevents Flash from loading at least in IE.
258 container
.style
.position
= "absolute";
259 container
.style
.left
= "-100px";
260 container
.style
.top
= "-100px";
261 var holder
= document
.createElement("div");
262 holder
.id
= "webSocketFlash";
263 container
.appendChild(holder
);
264 document
.body
.appendChild(container
);
266 WebSocket
.__swfLocation
, "webSocketFlash", "8", "8", "9.0.0",
267 null, {bridgeName
: "webSocket"}, null, null,
269 if (!e
.success
) console
.error("[WebSocket] swfobject.embedSWF failed");
272 FABridge
.addInitializationCallback("webSocket", function() {
274 //console.log("[WebSocket] FABridge initializad");
275 WebSocket
.__flash
= FABridge
.webSocket
.root();
276 WebSocket
.__flash
.setCallerUrl(location
.href
);
277 for (var i
= 0; i
< WebSocket
.__tasks
.length
; ++i
) {
278 WebSocket
.__tasks
[i
]();
280 WebSocket
.__tasks
= [];
282 console
.error("[WebSocket] " + e
.toString());
287 WebSocket
.__addTask = function(task
) {
288 if (WebSocket
.__flash
) {
291 WebSocket
.__tasks
.push(task
);
296 function webSocketLog(message
) {
297 console
.log(decodeURIComponent(message
));
301 function webSocketError(message
) {
302 console
.error(decodeURIComponent(message
));
306 if (window.addEventListener) {
307 window.addEventListener("load", WebSocket.__initialize, false);
309 window.attachEvent("onload", WebSocket.__initialize);