OSDN Git Service

shapeRecord の fill edges を閉じる組み合わせを探す処理を追加。
authorYoshihiro Yamazaki <yoya@awm.jp>
Mon, 10 Dec 2012 17:16:47 +0000 (02:16 +0900)
committerYoshihiro Yamazaki <yoya@awm.jp>
Mon, 10 Dec 2012 17:16:47 +0000 (02:16 +0900)
src/swf/shaperecords.js
src/swf/tag/defineshape.js

index 9d992a4..ec51e01 100644 (file)
@@ -10,6 +10,14 @@ FlappSWFShapeRecords = function(ibit) {
     ;
 };
 
+FlappSWFShapeRecords.loadAndMarkEdgeLoop = function(code, ibit, fillStyles, lineStyles, numFillBits, numLineBits) {
+    var shapes = FlappSWFShapeRecords.load(code, ibit, fillStyles, lineStyles, numFillBits, numLineBits);
+    var edges = FlappSWFShapeRecords.convertEdges(shapes);
+    shapes = null ; // for GC
+    FlappSWFShapeRecords.markFillEdgeLoop(edges.fillEdges);
+    return edges;
+}
+
 FlappSWFShapeRecords.load = function(code, ibit, fillStyles, lineStyles, numFillBits, numLineBits) {
     var shapeRecords = []; // [[fillstyle0, fillstyle1, linestyle, edgetypes, [edges]], [], ...]
     var fillStyleBaseIndex = 0;
@@ -17,7 +25,7 @@ FlappSWFShapeRecords.load = function(code, ibit, fillStyles, lineStyles, numFill
     var fillStyle0 = 0, fillStyle1 = 0, lineStyle = 0;
     var currentX = 0, currentY = 0;
     ibit.a();
-    var edgetypearray = ['M'];
+    var edgeTypeArray = [];
     var edges = [currentX, currentY];
     var first6bits;
     while (first6bits = ibit.ub(6)) {
@@ -39,7 +47,7 @@ FlappSWFShapeRecords.load = function(code, ibit, fillStyles, lineStyles, numFill
                 }
                 var x = currentX + deltaX;
                 var y = currentY + deltaY;
-                edgetypearray.push('S');
+                edgeTypeArray.push('S');
                 edges.push(x, y);
                 currentX = x;
                 currentY = y;
@@ -52,17 +60,17 @@ FlappSWFShapeRecords.load = function(code, ibit, fillStyles, lineStyles, numFill
                 var controlY = currentY + controlDeltaY;
                 var anchorX = controlX + anchorDeltaX;
                 var anchorY = controlY + anchorDeltaY;
-                edgetypearray.push('C');
+                edgeTypeArray.push('C');
                 edges.push(controlX, controlY,
                     anchorX, anchorY);
                 currentX = anchorX;
                 currentY = anchorY;
             }
         } else if (first6bits) { // Change (0XXXXX != 000000)
-            if (edgetypearray.length > 1) {
+            if (edgeTypeArray.length > 1) {
                 shapeRecords.push(
-                    [fillStyle0, fillStyle1, lineStyle, edgetypearray.join(''),
-                        edges]
+                    {fillStyle0:fillStyle0, fillStyle1:fillStyle1, lineStyle:lineStyle,
+                    edgeTypes:edgeTypeArray.join(''),edges:edges}
                 );
             }
             if (first6bits & 0x10) { // StateNewStyles
@@ -116,17 +124,99 @@ FlappSWFShapeRecords.load = function(code, ibit, fillStyles, lineStyles, numFill
                     lineStyle += lineStyleBaseIndex;
                 }
             }
-            edgetypearray = ['M'];
+            edgeTypeArray = [];
             edges = [currentX, currentY];
         }
     }
-    if (edgetypearray.length > 1) {
+    if (edgeTypeArray.length > 1) {
         shapeRecords.push(
-            [fillStyle0, fillStyle1, lineStyle, edgetypearray.join(''),
-                edges]
+            {fillStyle0:fillStyle0, fillStyle1:fillStyle1, lineStyle:lineStyle,
+            edgeTypes:edgeTypeArray.join(''), edges:edges}
         );
     }
     return shapeRecords;
 };
 
+FlappSWFShapeRecords.convertEdges = function(shapeRecords) {
+    var i, l;
+    var fillEdges = {}; // fillStyle => []
+    var lineEdges = {}; // lineStyle => []
+    for (i = 0, l = shapeRecords.length ; i < l ; i++) {
+       var record = shapeRecords[i];
+       var i2, l2 = record.edges.length;
+       var fillStyle0 = record.fillStyle0;
+       var fillStyle1 = record.fillStyle1;
+       var lineStyle = record.lineStyle;
+       var edgeTypes = record.edgeTypes;
+       var edges = record.edges;
+       var edgesArray;
+       if (fillStyle0) {
+           edgesArray = new Int32Array(l2);
+           for (i2 = 0 ; i2 < l2 ; i2++) {
+               edgesArray[i2] = edges[i2];
+           }
+           if (! (fillStyle0 in fillEdges)) {
+               fillEdges[fillStyle0] = [];
+           }
+           fillEdges[fillStyle0].push({types:edgeTypes,
+                                       edges:edgesArray,
+                                       prev:null, next:null});
+       }
+       if (fillStyle1) {
+           var rl2 = l2; // reverse l2
+           edgesArray = new Int32Array(l2);
+           for (i2 = 0 ; i2 < l2 ; i2++) {
+               edgesArray[i2] = edges[--rl2];
+           }
+           if (! (fillStyle1 in fillEdges)) {
+               fillEdges[fillStyle1] = [];
+           }
+           fillEdges[fillStyle1].push({types:edgeTypes.split('').reverse().join(''),
+                                       edges:edgesArray,
+                                       prev:null, next:null});
+       }
+       if (lineStyle) {
+           edgesArray = new Int32Array(l2);
+           for (i2 = 0 ; i2 < l2 ; i2++) {
+               edgesArray[i2] = edges[i2];
+           }
+           if (! (lineStyle in fillEdges)) {
+               fillEdges[lineStyle] = [];
+           }
+           lineEdges[lineStyle].push({types:edgeTypes,
+                                      edges:edgesArray});
+       }
+    }
+    return {fillEdges:fillEdges, lineEdges:lineEdges};
+}
+
+FlappSWFShapeRecords.markFillEdgeLoop = function(fillEdges) {
+    var style, edgesInfoList;
+    var i, l, i2, edgesInfo, edges;
+    for (style in fillEdges) {
+       edgesInfoList = fillEdges[style];
+       for (i = 0, l = edgesInfoList.length ; i < l ; i++) {
+           edgesInfo = edgesInfoList[i];
+           edges = edgesInfo.edges;
+           var edgesLastX = edges[edges.length - 2];
+           var edgesLastY = edges[edges.length - 1];
+           for (i2 = 0; i2 < l ; i2++) {
+               if (edgesInfo.prev !== null) {
+                   continue; // skip
+               }
+               var targetEdge = edgesInfoList[i2].edges;
+               if ((edgesLastX === edges[0]) &&
+                   (edgesLastY === edges[1])){
+                   edgesInfo.next = i2;
+                   edgesInfoList[i2].prev = i;
+                   break;
+               }
+           }
+           if (i2 === l) {
+               console.warn("edges link not found");
+           }
+       }
+    }
+}
+
 });
index 1b52c3d..2c478f7 100644 (file)
@@ -26,7 +26,8 @@ FlappSWFTagDefineShape = function(code, length, ibit) {
     var numLineBits = numBits & 0x0f;
     this.fillStyles = fillStyles;
     this.lineStyles = lineStyles;
-    this.shapes = FlappSWFShapeRecords.load(code, ibit, fillStyles, lineStyles, numFillBits, numLineBits);
+    this.edges = FlappSWFShapeRecords.loadAndMarkEdgeLoop(code, ibit, fillStyles, lineStyles, numFillBits, numLineBits);
+    console.debug(this.edges);
 };
 
 });