@melonjs/spine-plugin 1.2.1 → 1.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +10 -4
- package/README.md +1 -1
- package/dist/@melonjs/spine-plugin.d.ts +3 -1
- package/dist/@melonjs/spine-plugin.js +131 -40
- package/package.json +6 -6
- package/src/SkeletonRenderer.js +132 -41
package/CHANGELOG.md
CHANGED
|
@@ -1,19 +1,25 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
-
## 1.
|
|
3
|
+
## 1.3.0 - 2023-08-28å
|
|
4
|
+
|
|
5
|
+
- add support for Mesh Attachement
|
|
6
|
+
- added more examples under the test folder and separated them into individual files
|
|
7
|
+
- add a fullscreen option to examples (pressing the "F" key toggles fullscreen mode)
|
|
8
|
+
|
|
9
|
+
## 1.2.1 - 2023-08-23
|
|
4
10
|
|
|
5
11
|
- code refactoring and optimization to prepare for future feature additions
|
|
6
12
|
- fix URLs in the package.json file
|
|
7
13
|
|
|
8
|
-
## 1.2.0 -
|
|
14
|
+
## 1.2.0 - 2023-08-22
|
|
9
15
|
|
|
10
16
|
- add support for clipping (coin example is now rendered properly)
|
|
11
17
|
|
|
12
|
-
## 1.1.0 -
|
|
18
|
+
## 1.1.0 - 2023-08-19
|
|
13
19
|
|
|
14
20
|
- add some basic debug rendering
|
|
15
21
|
- optimize code (remove unneeded logic)
|
|
16
22
|
|
|
17
|
-
## 1.0.0 -
|
|
23
|
+
## 1.0.0 - 2023-08-16
|
|
18
24
|
|
|
19
25
|
initial release
|
package/README.md
CHANGED
|
@@ -14,7 +14,7 @@ a [Spine](http://en.esotericsoftware.com/spine-in-depth) 4.1 plugin implementati
|
|
|
14
14
|
Installation
|
|
15
15
|
-------------------------------------------------------------------------------
|
|
16
16
|
this plugin is already bundled with the required Spine runtime, so there is no need to install it separately.
|
|
17
|
-
>Note: this plugin requires melonJS version 15.9 or higher.
|
|
17
|
+
>Note: this plugin requires melonJS version 15.9.2 or higher.
|
|
18
18
|
|
|
19
19
|
To install the plugin using npm :
|
|
20
20
|
|
|
@@ -4073,12 +4073,14 @@ declare class SkeletonRenderer {
|
|
|
4073
4073
|
skeletonRenderer: any;
|
|
4074
4074
|
runtime: any;
|
|
4075
4075
|
tintColor: Color$1;
|
|
4076
|
-
|
|
4076
|
+
tempColor: Color$1;
|
|
4077
4077
|
debugRendering: boolean;
|
|
4078
4078
|
clipper: SkeletonClipping;
|
|
4079
4079
|
clippingVertices: any[];
|
|
4080
4080
|
clippingMask: Polygon;
|
|
4081
4081
|
draw(renderer: any, skeleton: any): void;
|
|
4082
|
+
drawTriangle(renderer: any, img: any, x0: any, y0: any, u0: any, v0: any, x1: any, y1: any, u1: any, v1: any, x2: any, y2: any, u2: any, v2: any): void;
|
|
4083
|
+
computeMeshVertices(slot: any, mesh: any, pma: boolean | undefined, vertexSize: any): void;
|
|
4082
4084
|
}
|
|
4083
4085
|
import { Vector2d } from 'melonjs';
|
|
4084
4086
|
/******************************************************************************
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/*!
|
|
2
|
-
* melonJS Spine plugin - v1.
|
|
2
|
+
* melonJS Spine plugin - v1.3.0
|
|
3
3
|
* http://www.melonjs.org
|
|
4
4
|
* @melonjs/spine-plugin is licensed under the MIT License.
|
|
5
5
|
* http://www.opensource.org/licenses/mit-license
|
|
@@ -14929,17 +14929,19 @@ class AssetManager {
|
|
|
14929
14929
|
}
|
|
14930
14930
|
}
|
|
14931
14931
|
|
|
14932
|
-
const
|
|
14932
|
+
const vertexSize = 2 + 2 + 4;
|
|
14933
14933
|
const blendModeLUT = ["normal", "additive", "multiply", "screen"];
|
|
14934
|
-
|
|
14935
14934
|
const regionDebugColor = "green";
|
|
14935
|
+
const meshDebugColor = "yellow";
|
|
14936
14936
|
const clipDebugColor = "blue";
|
|
14937
14937
|
|
|
14938
|
+
let worldVertices = new Float32Array(vertexSize * 1024);
|
|
14939
|
+
|
|
14938
14940
|
class SkeletonRenderer {
|
|
14939
14941
|
skeletonRenderer;
|
|
14940
14942
|
runtime;
|
|
14941
14943
|
tintColor = new Color$1();
|
|
14942
|
-
|
|
14944
|
+
tempColor = new Color$1();
|
|
14943
14945
|
debugRendering = false;
|
|
14944
14946
|
clipper = new SkeletonClipping();
|
|
14945
14947
|
clippingVertices = [];
|
|
@@ -14958,11 +14960,12 @@ class SkeletonRenderer {
|
|
|
14958
14960
|
let debugRendering = this.debugRendering;
|
|
14959
14961
|
|
|
14960
14962
|
for (var i = 0, n = drawOrder.length; i < n; i++) {
|
|
14961
|
-
let clippedVertexSize = clipper.isClipping() ? 2 :
|
|
14963
|
+
let clippedVertexSize = clipper.isClipping() ? 2 : vertexSize;
|
|
14962
14964
|
let slot = drawOrder[i];
|
|
14963
14965
|
let bone = slot.bone;
|
|
14964
14966
|
let image;
|
|
14965
14967
|
let region;
|
|
14968
|
+
let triangles;
|
|
14966
14969
|
|
|
14967
14970
|
if (!bone.active) {
|
|
14968
14971
|
clipper.clipEndWithSlot(slot);
|
|
@@ -14977,14 +14980,10 @@ class SkeletonRenderer {
|
|
|
14977
14980
|
region = attachment.region;
|
|
14978
14981
|
image = region.texture.getImage();
|
|
14979
14982
|
} else if (attachment instanceof MeshAttachment) {
|
|
14980
|
-
|
|
14981
|
-
|
|
14982
|
-
|
|
14983
|
-
|
|
14984
|
-
region = mesh.region;
|
|
14985
|
-
image = mesh.region.texture.getImage();
|
|
14986
|
-
*/
|
|
14987
|
-
console.warn("spine-plugin: MeshAttachment is not supported yet");
|
|
14983
|
+
this.computeMeshVertices(slot, attachment, false, clippedVertexSize);
|
|
14984
|
+
triangles = attachment.triangles;
|
|
14985
|
+
region = attachment.region;
|
|
14986
|
+
image = region.texture.getImage();
|
|
14988
14987
|
} else if (attachment instanceof ClippingAttachment) {
|
|
14989
14988
|
let clip = attachment;
|
|
14990
14989
|
let vertices = this.clippingVertices;
|
|
@@ -15008,43 +15007,55 @@ class SkeletonRenderer {
|
|
|
15008
15007
|
let blendMode = slot.data.blendMode;
|
|
15009
15008
|
let color = this.tintColor;
|
|
15010
15009
|
|
|
15010
|
+
renderer.save();
|
|
15011
|
+
|
|
15011
15012
|
color.setFloat(skeletonColor.r * slotColor.r * regionColor.r,
|
|
15012
15013
|
skeletonColor.g * slotColor.g * regionColor.g,
|
|
15013
15014
|
skeletonColor.b * slotColor.b * regionColor.b,
|
|
15014
15015
|
skeletonColor.a * slotColor.a * regionColor.a);
|
|
15015
15016
|
|
|
15016
|
-
renderer.
|
|
15017
|
-
renderer.transform(bone.a, bone.c, bone.b, bone.d, bone.worldX, bone.worldY);
|
|
15018
|
-
renderer.translate(attachment.offset[0], attachment.offset[1]);
|
|
15019
|
-
renderer.rotate(Math$1.degToRad(attachment.rotation));
|
|
15020
|
-
|
|
15021
|
-
let atlasScale = attachment.width / region.originalWidth;
|
|
15022
|
-
renderer.scale(atlasScale * attachment.scaleX, atlasScale * attachment.scaleY);
|
|
15023
|
-
|
|
15024
|
-
let w = region.width, h = region.height;
|
|
15025
|
-
let hW = w / 2, hH = h / 2;
|
|
15026
|
-
renderer.translate(hW, hH);
|
|
15027
|
-
if (region.degrees === 90) {
|
|
15028
|
-
let t = w;
|
|
15029
|
-
w = h;
|
|
15030
|
-
h = t;
|
|
15031
|
-
renderer.rotate(-Math$1.ETA);
|
|
15032
|
-
}
|
|
15033
|
-
renderer.scale(1, -1);
|
|
15034
|
-
renderer.translate(-hW, -hH);
|
|
15017
|
+
renderer.setGlobalAlpha(color.a);
|
|
15035
15018
|
renderer.setTint(color);
|
|
15036
15019
|
renderer.setBlendMode(blendModeLUT[blendMode]);
|
|
15037
|
-
renderer.setGlobalAlpha(color.a);
|
|
15038
15020
|
|
|
15039
|
-
if (
|
|
15040
|
-
|
|
15041
|
-
|
|
15021
|
+
if (typeof triangles !== "undefined") {
|
|
15022
|
+
let vertices = worldVertices;
|
|
15023
|
+
for (var j = 0; j < triangles.length; j += 3) {
|
|
15024
|
+
let t1 = triangles[j] * 8, t2 = triangles[j + 1] * 8, t3 = triangles[j + 2] * 8;
|
|
15025
|
+
let x0 = vertices[t1], y0 = vertices[t1 + 1], u0 = vertices[t1 + 6], v0 = vertices[t1 + 7];
|
|
15026
|
+
let x1 = vertices[t2], y1 = vertices[t2 + 1], u1 = vertices[t2 + 6], v1 = vertices[t2 + 7];
|
|
15027
|
+
let x2 = vertices[t3], y2 = vertices[t3 + 1], u2 = vertices[t3 + 6], v2 = vertices[t3 + 7];
|
|
15042
15028
|
|
|
15043
|
-
|
|
15029
|
+
this.drawTriangle(renderer, image, x0, y0, u0, v0, x1, y1, u1, v1, x2, y2, u2, v2);
|
|
15030
|
+
}
|
|
15031
|
+
} else {
|
|
15032
|
+
let atlasScale = attachment.width / region.originalWidth;
|
|
15033
|
+
let w = region.width, h = region.height;
|
|
15034
|
+
let hW = w / 2, hH = h / 2;
|
|
15044
15035
|
|
|
15045
|
-
|
|
15046
|
-
renderer.
|
|
15047
|
-
renderer.
|
|
15036
|
+
renderer.transform(bone.a, bone.c, bone.b, bone.d, bone.worldX, bone.worldY);
|
|
15037
|
+
renderer.translate(attachment.offset[0], attachment.offset[1]);
|
|
15038
|
+
renderer.rotate(Math$1.degToRad(attachment.rotation));
|
|
15039
|
+
renderer.scale(atlasScale * attachment.scaleX, atlasScale * attachment.scaleY);
|
|
15040
|
+
renderer.translate(hW, hH);
|
|
15041
|
+
if (region.degrees === 90) {
|
|
15042
|
+
let t = w;
|
|
15043
|
+
w = h;
|
|
15044
|
+
h = t;
|
|
15045
|
+
renderer.rotate(-Math$1.ETA);
|
|
15046
|
+
}
|
|
15047
|
+
renderer.scale(1, -1);
|
|
15048
|
+
renderer.translate(-hW, -hH);
|
|
15049
|
+
|
|
15050
|
+
if (clipper.isClipping()) {
|
|
15051
|
+
renderer.setMask(clippingMask);
|
|
15052
|
+
}
|
|
15053
|
+
renderer.drawImage(image, image.width * region.u, image.height * region.v, w, h, 0, 0, w, h);
|
|
15054
|
+
|
|
15055
|
+
if (debugRendering === true) {
|
|
15056
|
+
renderer.setColor(regionDebugColor);
|
|
15057
|
+
renderer.strokeRect(0, 0, w, h);
|
|
15058
|
+
}
|
|
15048
15059
|
}
|
|
15049
15060
|
|
|
15050
15061
|
renderer.restore();
|
|
@@ -15054,6 +15065,86 @@ class SkeletonRenderer {
|
|
|
15054
15065
|
}
|
|
15055
15066
|
clipper.clipEnd();
|
|
15056
15067
|
}
|
|
15068
|
+
|
|
15069
|
+
drawTriangle(renderer, img, x0, y0, u0, v0, x1, y1, u1, v1, x2, y2, u2, v2) {
|
|
15070
|
+
u0 *= img.width;
|
|
15071
|
+
v0 *= img.height;
|
|
15072
|
+
u1 *= img.width;
|
|
15073
|
+
v1 *= img.height;
|
|
15074
|
+
u2 *= img.width;
|
|
15075
|
+
v2 *= img.height;
|
|
15076
|
+
|
|
15077
|
+
renderer.save();
|
|
15078
|
+
renderer.beginPath();
|
|
15079
|
+
renderer.moveTo(x0, y0);
|
|
15080
|
+
renderer.lineTo(x1, y1);
|
|
15081
|
+
renderer.lineTo(x2, y2);
|
|
15082
|
+
renderer.closePath();
|
|
15083
|
+
renderer.setMask();
|
|
15084
|
+
|
|
15085
|
+
x1 -= x0;
|
|
15086
|
+
y1 -= y0;
|
|
15087
|
+
x2 -= x0;
|
|
15088
|
+
y2 -= y0;
|
|
15089
|
+
|
|
15090
|
+
u1 -= u0;
|
|
15091
|
+
v1 -= v0;
|
|
15092
|
+
u2 -= u0;
|
|
15093
|
+
v2 -= v0;
|
|
15094
|
+
|
|
15095
|
+
var det = 1 / (u1 * v2 - u2 * v1),
|
|
15096
|
+
|
|
15097
|
+
// linear transformation
|
|
15098
|
+
a = (v2 * x1 - v1 * x2) * det,
|
|
15099
|
+
b = (v2 * y1 - v1 * y2) * det,
|
|
15100
|
+
c = (u1 * x2 - u2 * x1) * det,
|
|
15101
|
+
d = (u1 * y2 - u2 * y1) * det,
|
|
15102
|
+
|
|
15103
|
+
// translation
|
|
15104
|
+
e = x0 - a * u0 - c * v0,
|
|
15105
|
+
f = y0 - b * u0 - d * v0;
|
|
15106
|
+
|
|
15107
|
+
renderer.transform(a, b, c, d, e, f);
|
|
15108
|
+
renderer.drawImage(img, 0, 0);
|
|
15109
|
+
renderer.clearMask();
|
|
15110
|
+
renderer.restore();
|
|
15111
|
+
|
|
15112
|
+
if (this.debugRendering === true) {
|
|
15113
|
+
renderer.setColor(meshDebugColor);
|
|
15114
|
+
renderer.stroke();
|
|
15115
|
+
}
|
|
15116
|
+
|
|
15117
|
+
}
|
|
15118
|
+
|
|
15119
|
+
computeMeshVertices(slot, mesh, pma = false, vertexSize) {
|
|
15120
|
+
let skeletonColor = slot.bone.skeleton.color;
|
|
15121
|
+
let slotColor = slot.color;
|
|
15122
|
+
let regionColor = mesh.color;
|
|
15123
|
+
let alpha = skeletonColor.a * slotColor.a * regionColor.a;
|
|
15124
|
+
let multiplier = pma ? alpha : 1;
|
|
15125
|
+
|
|
15126
|
+
this.tempColor.setFloat(skeletonColor.r * slotColor.r * regionColor.r * multiplier,
|
|
15127
|
+
skeletonColor.g * slotColor.g * regionColor.g * multiplier,
|
|
15128
|
+
skeletonColor.b * slotColor.b * regionColor.b * multiplier,
|
|
15129
|
+
alpha);
|
|
15130
|
+
|
|
15131
|
+
if (worldVertices.length < mesh.worldVerticesLength) worldVertices = new Float32Array(mesh.worldVerticesLength);
|
|
15132
|
+
mesh.computeWorldVertices(slot, 0, mesh.worldVerticesLength, worldVertices, 0, vertexSize);
|
|
15133
|
+
|
|
15134
|
+
let uvs = mesh.uvs;
|
|
15135
|
+
let color = this.tempColor.toArray();
|
|
15136
|
+
let vertices = worldVertices;
|
|
15137
|
+
let vertexCount = mesh.worldVerticesLength / 2;
|
|
15138
|
+
for (let i = 0, u = 0, v = 2; i < vertexCount; i++) {
|
|
15139
|
+
vertices[v++] = color[0];
|
|
15140
|
+
vertices[v++] = color[1];
|
|
15141
|
+
vertices[v++] = color[2];
|
|
15142
|
+
vertices[v++] = color[3];
|
|
15143
|
+
vertices[v++] = uvs[u++];
|
|
15144
|
+
vertices[v++] = uvs[u++];
|
|
15145
|
+
v += 2;
|
|
15146
|
+
}
|
|
15147
|
+
}
|
|
15057
15148
|
}
|
|
15058
15149
|
|
|
15059
15150
|
let assetManager = new AssetManager();
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@melonjs/spine-plugin",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.3.0",
|
|
4
4
|
"description": "melonJS Spine plugin",
|
|
5
5
|
"homepage": "https://github.com/melonjs/spine-plugin#readme",
|
|
6
6
|
"type": "module",
|
|
@@ -46,7 +46,7 @@
|
|
|
46
46
|
"CHANGELOG.md"
|
|
47
47
|
],
|
|
48
48
|
"peerDependencies": {
|
|
49
|
-
"melonjs": "^15.9.
|
|
49
|
+
"melonjs": "^15.9.2"
|
|
50
50
|
},
|
|
51
51
|
"dependencies": {
|
|
52
52
|
"@esotericsoftware/spine-canvas": "^4.2.18",
|
|
@@ -54,17 +54,17 @@
|
|
|
54
54
|
"@esotericsoftware/spine-webgl": "^4.2.18"
|
|
55
55
|
},
|
|
56
56
|
"devDependencies": {
|
|
57
|
-
"@babel/eslint-parser": "^7.22.
|
|
57
|
+
"@babel/eslint-parser": "^7.22.11",
|
|
58
58
|
"@babel/plugin-syntax-import-assertions": "^7.22.5",
|
|
59
59
|
"@rollup/plugin-commonjs": "^25.0.4",
|
|
60
60
|
"@rollup/plugin-node-resolve": "^15.2.1",
|
|
61
61
|
"@rollup/plugin-replace": "^5.0.2",
|
|
62
|
-
"del-cli": "^5.0.
|
|
63
|
-
"eslint": "^8.
|
|
62
|
+
"del-cli": "^5.0.1",
|
|
63
|
+
"eslint": "^8.48.0",
|
|
64
64
|
"eslint-plugin-jsdoc": "^46.5.0",
|
|
65
65
|
"rollup": "^3.28.1",
|
|
66
66
|
"rollup-plugin-bundle-size": "^1.0.3",
|
|
67
|
-
"typescript": "^5.
|
|
67
|
+
"typescript": "^5.2.2"
|
|
68
68
|
},
|
|
69
69
|
"scripts": {
|
|
70
70
|
"build": "npm run clean && npm run lint && rollup -c --silent && npm run types",
|
package/src/SkeletonRenderer.js
CHANGED
|
@@ -1,17 +1,19 @@
|
|
|
1
1
|
import { Color as MColor, Math as MMath, Polygon } from "melonjs";
|
|
2
2
|
import { SkeletonClipping, ClippingAttachment, MeshAttachment, RegionAttachment } from "@esotericsoftware/spine-core";
|
|
3
3
|
|
|
4
|
-
const
|
|
4
|
+
const vertexSize = 2 + 2 + 4;
|
|
5
5
|
const blendModeLUT = ["normal", "additive", "multiply", "screen"];
|
|
6
|
-
|
|
7
6
|
const regionDebugColor = "green";
|
|
7
|
+
const meshDebugColor = "yellow";
|
|
8
8
|
const clipDebugColor = "blue";
|
|
9
9
|
|
|
10
|
+
let worldVertices = new Float32Array(vertexSize * 1024);
|
|
11
|
+
|
|
10
12
|
export default class SkeletonRenderer {
|
|
11
13
|
skeletonRenderer;
|
|
12
14
|
runtime;
|
|
13
15
|
tintColor = new MColor();
|
|
14
|
-
|
|
16
|
+
tempColor = new MColor();
|
|
15
17
|
debugRendering = false;
|
|
16
18
|
clipper = new SkeletonClipping();
|
|
17
19
|
clippingVertices = [];
|
|
@@ -30,11 +32,12 @@ export default class SkeletonRenderer {
|
|
|
30
32
|
let debugRendering = this.debugRendering;
|
|
31
33
|
|
|
32
34
|
for (var i = 0, n = drawOrder.length; i < n; i++) {
|
|
33
|
-
let clippedVertexSize = clipper.isClipping() ? 2 :
|
|
35
|
+
let clippedVertexSize = clipper.isClipping() ? 2 : vertexSize;
|
|
34
36
|
let slot = drawOrder[i];
|
|
35
37
|
let bone = slot.bone;
|
|
36
38
|
let image;
|
|
37
39
|
let region;
|
|
40
|
+
let triangles;
|
|
38
41
|
|
|
39
42
|
if (!bone.active) {
|
|
40
43
|
clipper.clipEndWithSlot(slot);
|
|
@@ -49,14 +52,10 @@ export default class SkeletonRenderer {
|
|
|
49
52
|
region = attachment.region;
|
|
50
53
|
image = region.texture.getImage();
|
|
51
54
|
} else if (attachment instanceof MeshAttachment) {
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
region = mesh.region;
|
|
57
|
-
image = mesh.region.texture.getImage();
|
|
58
|
-
*/
|
|
59
|
-
console.warn("spine-plugin: MeshAttachment is not supported yet");
|
|
55
|
+
this.computeMeshVertices(slot, attachment, false, clippedVertexSize);
|
|
56
|
+
triangles = attachment.triangles;
|
|
57
|
+
region = attachment.region;
|
|
58
|
+
image = region.texture.getImage();
|
|
60
59
|
} else if (attachment instanceof ClippingAttachment) {
|
|
61
60
|
let clip = attachment;
|
|
62
61
|
let vertices = this.clippingVertices;
|
|
@@ -80,43 +79,55 @@ export default class SkeletonRenderer {
|
|
|
80
79
|
let blendMode = slot.data.blendMode;
|
|
81
80
|
let color = this.tintColor;
|
|
82
81
|
|
|
82
|
+
renderer.save();
|
|
83
|
+
|
|
83
84
|
color.setFloat(skeletonColor.r * slotColor.r * regionColor.r,
|
|
84
85
|
skeletonColor.g * slotColor.g * regionColor.g,
|
|
85
86
|
skeletonColor.b * slotColor.b * regionColor.b,
|
|
86
87
|
skeletonColor.a * slotColor.a * regionColor.a);
|
|
87
88
|
|
|
88
|
-
renderer.
|
|
89
|
-
renderer.transform(bone.a, bone.c, bone.b, bone.d, bone.worldX, bone.worldY);
|
|
90
|
-
renderer.translate(attachment.offset[0], attachment.offset[1]);
|
|
91
|
-
renderer.rotate(MMath.degToRad(attachment.rotation));
|
|
92
|
-
|
|
93
|
-
let atlasScale = attachment.width / region.originalWidth;
|
|
94
|
-
renderer.scale(atlasScale * attachment.scaleX, atlasScale * attachment.scaleY);
|
|
95
|
-
|
|
96
|
-
let w = region.width, h = region.height;
|
|
97
|
-
let hW = w / 2, hH = h / 2;
|
|
98
|
-
renderer.translate(hW, hH);
|
|
99
|
-
if (region.degrees === 90) {
|
|
100
|
-
let t = w;
|
|
101
|
-
w = h;
|
|
102
|
-
h = t;
|
|
103
|
-
renderer.rotate(-MMath.ETA);
|
|
104
|
-
}
|
|
105
|
-
renderer.scale(1, -1);
|
|
106
|
-
renderer.translate(-hW, -hH);
|
|
89
|
+
renderer.setGlobalAlpha(color.a);
|
|
107
90
|
renderer.setTint(color);
|
|
108
91
|
renderer.setBlendMode(blendModeLUT[blendMode]);
|
|
109
|
-
renderer.setGlobalAlpha(color.a);
|
|
110
92
|
|
|
111
|
-
if (
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
93
|
+
if (typeof triangles !== "undefined") {
|
|
94
|
+
let vertices = worldVertices;
|
|
95
|
+
for (var j = 0; j < triangles.length; j += 3) {
|
|
96
|
+
let t1 = triangles[j] * 8, t2 = triangles[j + 1] * 8, t3 = triangles[j + 2] * 8;
|
|
97
|
+
let x0 = vertices[t1], y0 = vertices[t1 + 1], u0 = vertices[t1 + 6], v0 = vertices[t1 + 7];
|
|
98
|
+
let x1 = vertices[t2], y1 = vertices[t2 + 1], u1 = vertices[t2 + 6], v1 = vertices[t2 + 7];
|
|
99
|
+
let x2 = vertices[t3], y2 = vertices[t3 + 1], u2 = vertices[t3 + 6], v2 = vertices[t3 + 7];
|
|
100
|
+
|
|
101
|
+
this.drawTriangle(renderer, image, x0, y0, u0, v0, x1, y1, u1, v1, x2, y2, u2, v2);
|
|
102
|
+
}
|
|
103
|
+
} else {
|
|
104
|
+
let atlasScale = attachment.width / region.originalWidth;
|
|
105
|
+
let w = region.width, h = region.height;
|
|
106
|
+
let hW = w / 2, hH = h / 2;
|
|
107
|
+
|
|
108
|
+
renderer.transform(bone.a, bone.c, bone.b, bone.d, bone.worldX, bone.worldY);
|
|
109
|
+
renderer.translate(attachment.offset[0], attachment.offset[1]);
|
|
110
|
+
renderer.rotate(MMath.degToRad(attachment.rotation));
|
|
111
|
+
renderer.scale(atlasScale * attachment.scaleX, atlasScale * attachment.scaleY);
|
|
112
|
+
renderer.translate(hW, hH);
|
|
113
|
+
if (region.degrees === 90) {
|
|
114
|
+
let t = w;
|
|
115
|
+
w = h;
|
|
116
|
+
h = t;
|
|
117
|
+
renderer.rotate(-MMath.ETA);
|
|
118
|
+
}
|
|
119
|
+
renderer.scale(1, -1);
|
|
120
|
+
renderer.translate(-hW, -hH);
|
|
121
|
+
|
|
122
|
+
if (clipper.isClipping()) {
|
|
123
|
+
renderer.setMask(clippingMask);
|
|
124
|
+
}
|
|
125
|
+
renderer.drawImage(image, image.width * region.u, image.height * region.v, w, h, 0, 0, w, h);
|
|
126
|
+
|
|
127
|
+
if (debugRendering === true) {
|
|
128
|
+
renderer.setColor(regionDebugColor);
|
|
129
|
+
renderer.strokeRect(0, 0, w, h);
|
|
130
|
+
}
|
|
120
131
|
}
|
|
121
132
|
|
|
122
133
|
renderer.restore();
|
|
@@ -126,4 +137,84 @@ export default class SkeletonRenderer {
|
|
|
126
137
|
}
|
|
127
138
|
clipper.clipEnd();
|
|
128
139
|
}
|
|
140
|
+
|
|
141
|
+
drawTriangle(renderer, img, x0, y0, u0, v0, x1, y1, u1, v1, x2, y2, u2, v2) {
|
|
142
|
+
u0 *= img.width;
|
|
143
|
+
v0 *= img.height;
|
|
144
|
+
u1 *= img.width;
|
|
145
|
+
v1 *= img.height;
|
|
146
|
+
u2 *= img.width;
|
|
147
|
+
v2 *= img.height;
|
|
148
|
+
|
|
149
|
+
renderer.save();
|
|
150
|
+
renderer.beginPath();
|
|
151
|
+
renderer.moveTo(x0, y0);
|
|
152
|
+
renderer.lineTo(x1, y1);
|
|
153
|
+
renderer.lineTo(x2, y2);
|
|
154
|
+
renderer.closePath();
|
|
155
|
+
renderer.setMask();
|
|
156
|
+
|
|
157
|
+
x1 -= x0;
|
|
158
|
+
y1 -= y0;
|
|
159
|
+
x2 -= x0;
|
|
160
|
+
y2 -= y0;
|
|
161
|
+
|
|
162
|
+
u1 -= u0;
|
|
163
|
+
v1 -= v0;
|
|
164
|
+
u2 -= u0;
|
|
165
|
+
v2 -= v0;
|
|
166
|
+
|
|
167
|
+
var det = 1 / (u1 * v2 - u2 * v1),
|
|
168
|
+
|
|
169
|
+
// linear transformation
|
|
170
|
+
a = (v2 * x1 - v1 * x2) * det,
|
|
171
|
+
b = (v2 * y1 - v1 * y2) * det,
|
|
172
|
+
c = (u1 * x2 - u2 * x1) * det,
|
|
173
|
+
d = (u1 * y2 - u2 * y1) * det,
|
|
174
|
+
|
|
175
|
+
// translation
|
|
176
|
+
e = x0 - a * u0 - c * v0,
|
|
177
|
+
f = y0 - b * u0 - d * v0;
|
|
178
|
+
|
|
179
|
+
renderer.transform(a, b, c, d, e, f);
|
|
180
|
+
renderer.drawImage(img, 0, 0);
|
|
181
|
+
renderer.clearMask();
|
|
182
|
+
renderer.restore();
|
|
183
|
+
|
|
184
|
+
if (this.debugRendering === true) {
|
|
185
|
+
renderer.setColor(meshDebugColor);
|
|
186
|
+
renderer.stroke();
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
computeMeshVertices(slot, mesh, pma = false, vertexSize) {
|
|
192
|
+
let skeletonColor = slot.bone.skeleton.color;
|
|
193
|
+
let slotColor = slot.color;
|
|
194
|
+
let regionColor = mesh.color;
|
|
195
|
+
let alpha = skeletonColor.a * slotColor.a * regionColor.a;
|
|
196
|
+
let multiplier = pma ? alpha : 1;
|
|
197
|
+
|
|
198
|
+
this.tempColor.setFloat(skeletonColor.r * slotColor.r * regionColor.r * multiplier,
|
|
199
|
+
skeletonColor.g * slotColor.g * regionColor.g * multiplier,
|
|
200
|
+
skeletonColor.b * slotColor.b * regionColor.b * multiplier,
|
|
201
|
+
alpha);
|
|
202
|
+
|
|
203
|
+
if (worldVertices.length < mesh.worldVerticesLength) worldVertices = new Float32Array(mesh.worldVerticesLength);
|
|
204
|
+
mesh.computeWorldVertices(slot, 0, mesh.worldVerticesLength, worldVertices, 0, vertexSize);
|
|
205
|
+
|
|
206
|
+
let uvs = mesh.uvs;
|
|
207
|
+
let color = this.tempColor.toArray();
|
|
208
|
+
let vertices = worldVertices;
|
|
209
|
+
let vertexCount = mesh.worldVerticesLength / 2;
|
|
210
|
+
for (let i = 0, u = 0, v = 2; i < vertexCount; i++) {
|
|
211
|
+
vertices[v++] = color[0];
|
|
212
|
+
vertices[v++] = color[1];
|
|
213
|
+
vertices[v++] = color[2];
|
|
214
|
+
vertices[v++] = color[3];
|
|
215
|
+
vertices[v++] = uvs[u++];
|
|
216
|
+
vertices[v++] = uvs[u++];
|
|
217
|
+
v += 2;
|
|
218
|
+
}
|
|
219
|
+
}
|
|
129
220
|
}
|