浏览代码

Opera fixes and big Opera performance boost.

Add message/state pollling in web-socket-js. Since Opera tends to drop
message events, we can dramatically increase performance by polling
every now for message event data.

Also, add more direct calls to update readyState so that it's not
missed when Opera drops events.
Joel Martin 15 年之前
父节点
当前提交
bc8e3d4db7
共有 3 个文件被更改,包括 48 次插入26 次删除
  1. 2 3
      docs/TODO
  2. 1 1
      include/vnc.js
  3. 45 22
      include/web-socket-js/web_socket.js

+ 2 - 3
docs/TODO

@@ -2,9 +2,6 @@ Short Term:
 
 - Test on IE 9 preview 3.
 
-- Track down "INVALID_STATE_ERR" when reconnecting using
-  web-socket-js.
-
 - Possibly support IE <= 8.0 using excanvas or fxcanvas:
   http://excanvas.sourceforge.net/
   http://code.google.com/p/fxcanvas/
@@ -12,6 +9,8 @@ Short Term:
 - Timing delta between frames in proxy record log, for playback
   support (for demo and test).
 
+- Track down hang in Opera after second disconnect.
+
 
 Medium Term:
 

+ 1 - 1
include/vnc.js

@@ -194,9 +194,9 @@ connect: function (host, port, password, encrypt, true_color) {
 disconnect: function () {
     //console.log(">> disconnect");
     if ((RFB.ws) && (RFB.ws.readyState === WebSocket.OPEN)) {
+        RFB.ws.close();
         RFB.updateState('closed');
         RFB.ws.onmessage = function (e) { return; };
-        RFB.ws.close();
     }
     if (Canvas.ctx) {
         Canvas.stop();

+ 45 - 22
include/web-socket-js/web_socket.js

@@ -35,8 +35,40 @@
       self.__flash =
         WebSocket.__flash.create(url, protocol, proxyHost || null, proxyPort || 0, headers || null);
 
+      self.__messageHandler = function() {
+        var i, arr, data;
+        arr = self.__flash.readSocketData();
+        for (i=0; i < arr.length; i++) {
+          data = decodeURIComponent(arr[i]);
+          try {
+            if (self.onmessage) {
+              var e;
+              if (window.MessageEvent) {
+                e = document.createEvent("MessageEvent");
+                e.initMessageEvent("message", false, false, data, null, null, window, null);
+              } else { // IE
+                e = {data: data};
+              }
+              self.onmessage(e);
+            }
+          } catch (e) {
+            console.error(e.toString());
+          }
+        }
+      };
+
       self.__flash.addEventListener("open", function(fe) {
-        console.log("web-socket.js open");
+        self.readyState = self.__flash.getReadyState();
+
+        // For browsers (like Opera) that drop events, also poll for
+        // message data
+        if (self.__messageHandlerID) {
+          clearInterval(self.__messageHandlerID);
+        }
+        self.__messageHandlerID = setInterval(function () {
+            //console.log("polling for message data");
+            self.__messageHandler; }, 500);
+
         try {
           if (self.onopen) {
             self.onopen();
@@ -52,6 +84,11 @@
       });
 
       self.__flash.addEventListener("close", function(fe) {
+        self.readyState = self.__flash.getReadyState();
+
+        if (self.__messageHandlerID) {
+          clearInterval(self.__messageHandlerID);
+        }
         try {
           if (self.onclose) self.onclose();
         } catch (e) {
@@ -59,29 +96,12 @@
         }
       });
 
-      self.__flash.addEventListener("message", function(fe) {
-        var i, arr, data;
-        arr = self.__flash.readSocketData();
-        for (i=0; i < arr.length; i++) {
-          data = decodeURIComponent(arr[i]);
-          try {
-            if (self.onmessage) {
-              var e;
-              if (window.MessageEvent) {
-                e = document.createEvent("MessageEvent");
-                e.initMessageEvent("message", false, false, data, null, null, window, null);
-              } else { // IE
-                e = {data: data};
-              }
-              self.onmessage(e);
-            }
-          } catch (e) {
-            console.error(e.toString());
-          }
-        }
-      });
+      self.__flash.addEventListener("message", self.__messageHandler);
 
       self.__flash.addEventListener("error", function(fe) {
+        if (self.__messageHandlerID) {
+          clearInterval(self.__messageHandlerID);
+        }
         try {
           if (self.onerror) self.onerror();
         } catch (e) {
@@ -125,6 +145,9 @@
     // which causes weird error:
     // > You are trying to call recursively into the Flash Player which is not allowed.
     this.readyState = WebSocket.CLOSED;
+    if (this.__messageHandlerID) {
+      clearInterval(this.__messageHandlerID);
+    }
     if (this.onclose) this.onclose();
   };