ag-psd 30.1.1 → 30.2.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/.v8-cache/v24.13.1-x64-cf738c9d/017325ac +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/043c7b90 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/05135617 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/059f8558 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/0706ecb8 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/0db754a7 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/1130885f +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/15f0e479 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/20477c23 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/20dfa422 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/2a19133e +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/2b069ee0 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/2de09439 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/2e44f5f0 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/2fb229a9 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/3144b401 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/37481985 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/4511bacf +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/49d22b79 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/4f5702bd +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/514cc428 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/57d3380b +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/6024ce3f +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/61735b23 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/63dbdb75 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/6cbfc0ec +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/6f08372c +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/7100ee08 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/71df9cb3 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/75e41e43 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/7ea06cea +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/8568576b +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/87372817 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/87cf2209 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/932f0770 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/a79a40bb +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/a7e80865 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/acc36e66 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/b3c2fab7 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/b69ed3a3 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/bdff1628 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/c0b789d2 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/c314aece +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/cfc49f4f +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/cff9434a +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/d02dd6f7 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/dc86f000 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/de74e659 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/e03e2acd +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/e158d332 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/e6735171 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/e6745c2b +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/e6b99945 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/eeeebdfe +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/fbca6276 +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/fc97d72d +0 -0
- package/.v8-cache/v24.13.1-x64-cf738c9d/fd0a2987 +0 -0
- package/CHANGELOG.md +3 -0
- package/README.md +1 -1
- package/README_PSD.md +1 -1
- package/dist/abr.js +43 -56
- package/dist/abr.js.map +1 -1
- package/dist/additionalInfo.js +770 -808
- package/dist/additionalInfo.js.map +1 -1
- package/dist/ase.js +21 -21
- package/dist/ase.js.map +1 -1
- package/dist/bundle.js +2592 -2778
- package/dist/csh.js +18 -29
- package/dist/csh.js.map +1 -1
- package/dist/descriptor.js +234 -269
- package/dist/descriptor.js.map +1 -1
- package/dist/effectsHelpers.js +91 -112
- package/dist/effectsHelpers.js.map +1 -1
- package/dist/engineData.js +45 -51
- package/dist/engineData.js.map +1 -1
- package/dist/engineData2.js +8 -9
- package/dist/engineData2.js.map +1 -1
- package/dist/helpers.js +75 -81
- package/dist/helpers.js.map +1 -1
- package/dist/imageResources.js +342 -381
- package/dist/imageResources.js.map +1 -1
- package/dist/index.js +6 -6
- package/dist/index.js.map +1 -1
- package/dist/initializeCanvas.js +2 -2
- package/dist/initializeCanvas.js.map +1 -1
- package/dist/jpeg.js +279 -279
- package/dist/jpeg.js.map +1 -1
- package/dist/psdReader.js +336 -347
- package/dist/psdReader.js.map +1 -1
- package/dist/psdWriter.d.ts +2 -1
- package/dist/psdWriter.js +225 -206
- package/dist/psdWriter.js.map +1 -1
- package/dist/text.js +98 -122
- package/dist/text.js.map +1 -1
- package/dist/utf8.js +22 -22
- package/dist/utf8.js.map +1 -1
- package/dist-es/abr.js +41 -54
- package/dist-es/abr.js.map +1 -1
- package/dist-es/additionalInfo.js +765 -803
- package/dist-es/additionalInfo.js.map +1 -1
- package/dist-es/ase.js +20 -20
- package/dist-es/ase.js.map +1 -1
- package/dist-es/csh.js +16 -27
- package/dist-es/csh.js.map +1 -1
- package/dist-es/descriptor.js +284 -319
- package/dist-es/descriptor.js.map +1 -1
- package/dist-es/effectsHelpers.js +88 -109
- package/dist-es/effectsHelpers.js.map +1 -1
- package/dist-es/engineData.js +45 -51
- package/dist-es/engineData.js.map +1 -1
- package/dist-es/engineData2.js +8 -9
- package/dist-es/engineData2.js.map +1 -1
- package/dist-es/helpers.js +79 -85
- package/dist-es/helpers.js.map +1 -1
- package/dist-es/imageResources.js +338 -377
- package/dist-es/imageResources.js.map +1 -1
- package/dist-es/index.js +4 -4
- package/dist-es/index.js.map +1 -1
- package/dist-es/jpeg.js +279 -279
- package/dist-es/jpeg.js.map +1 -1
- package/dist-es/psdReader.js +333 -344
- package/dist-es/psdReader.js.map +1 -1
- package/dist-es/psdWriter.d.ts +2 -1
- package/dist-es/psdWriter.js +220 -202
- package/dist-es/psdWriter.js.map +1 -1
- package/dist-es/text.js +98 -122
- package/dist-es/text.js.map +1 -1
- package/dist-es/utf8.js +22 -22
- package/dist-es/utf8.js.map +1 -1
- package/package.json +1 -1
- package/publish.js +24 -0
- package/src/additionalInfo.ts +15 -11
- package/src/psdWriter.ts +76 -1
- package/tsconfig.json +4 -3
|
@@ -1,28 +1,17 @@
|
|
|
1
|
-
var __assign = (this && this.__assign) || function () {
|
|
2
|
-
__assign = Object.assign || function(t) {
|
|
3
|
-
for (var s, i = 1, n = arguments.length; i < n; i++) {
|
|
4
|
-
s = arguments[i];
|
|
5
|
-
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
|
|
6
|
-
t[p] = s[p];
|
|
7
|
-
}
|
|
8
|
-
return t;
|
|
9
|
-
};
|
|
10
|
-
return __assign.apply(this, arguments);
|
|
11
|
-
};
|
|
12
1
|
import { fromByteArray, toByteArray } from 'base64-js';
|
|
13
2
|
import { readEffects, writeEffects } from './effectsHelpers';
|
|
14
3
|
import { clamp, createEnum, layerColors, MOCK_HANDLERS } from './helpers';
|
|
15
4
|
import { readSignature, readUnicodeString, skipBytes, readUint32, readUint8, readFloat64, readUint16, readBytes, readInt16, checkSignature, readFloat32, readFixedPointPath32, readSection, readColor, readInt32, readPascalString, readUnicodeStringWithLength, readAsciiString, readPattern, readLayerInfo } from './psdReader';
|
|
16
|
-
import { writeZeros, writeSignature, writeBytes, writeUint32, writeUint16, writeFloat64, writeUint8, writeInt16, writeFloat32, writeFixedPointPath32, writeUnicodeString, writeSection, writeUnicodeStringWithPadding, writeColor, writePascalString, writeInt32 } from './psdWriter';
|
|
5
|
+
import { writeZeros, writeSignature, writeBytes, writeUint32, writeUint16, writeFloat64, writeUint8, writeInt16, writeFloat32, writeFixedPointPath32, writeUnicodeString, writeSection, writeUnicodeStringWithPadding, writeColor, writePascalString, writeInt32, writePattern } from './psdWriter';
|
|
17
6
|
import { Annt, BlnM, parsePercent, parseUnits, parseUnitsOrNumber, strokeStyleLineAlignment, strokeStyleLineCapType, strokeStyleLineJoinType, textGridding, unitsPercent, unitsValue, warpStyle, writeVersionAndDescriptor, readVersionAndDescriptor, Ornt, horzVrtcToXY, xyToHorzVrtc, serializeEffects, parseEffects, parseColor, serializeColor, serializeVectorContent, parseVectorContent, parseTrackList, serializeTrackList, BlrM, BlrQ, SmBQ, SmBM, DspM, UndA, Cnvr, RplS, SphM, Wvtp, ZZTy, Dstr, Chnl, MztT, Lns, blurType, DfsM, ExtT, ExtR, FlCl, CntE, WndM, Drct, IntE, IntC, FlMd, unitsPercentF, frac, ClrS, descBoundsToBounds, boundsToDescBounds, presetKindType, gradientInterpolationMethodType } from './descriptor';
|
|
18
7
|
import { serializeEngineData, parseEngineData } from './engineData';
|
|
19
8
|
import { encodeEngineData, decodeEngineData } from './text';
|
|
20
9
|
import { decodeEngineData2 } from './engineData2';
|
|
21
|
-
|
|
22
|
-
export
|
|
23
|
-
export
|
|
10
|
+
const fromAtoZ = 'abcdefghijklmnopqrstuvwxyz';
|
|
11
|
+
export const infoHandlers = [];
|
|
12
|
+
export const infoHandlersMap = {};
|
|
24
13
|
function addHandler(key, has, read, write) {
|
|
25
|
-
|
|
14
|
+
const handler = { key, has, read, write };
|
|
26
15
|
infoHandlers.push(handler);
|
|
27
16
|
infoHandlersMap[handler.key] = handler;
|
|
28
17
|
}
|
|
@@ -30,33 +19,33 @@ function addHandlerAlias(key, target) {
|
|
|
30
19
|
infoHandlersMap[key] = infoHandlersMap[target];
|
|
31
20
|
}
|
|
32
21
|
function hasKey(key) {
|
|
33
|
-
return
|
|
22
|
+
return (target) => target[key] !== undefined;
|
|
34
23
|
}
|
|
35
24
|
function readLength64(reader) {
|
|
36
25
|
if (readUint32(reader))
|
|
37
|
-
throw new Error(
|
|
26
|
+
throw new Error(`Resource size above 4 GB limit at ${reader.offset.toString(16)}`);
|
|
38
27
|
return readUint32(reader);
|
|
39
28
|
}
|
|
40
29
|
function writeLength64(writer, length) {
|
|
41
30
|
writeUint32(writer, 0);
|
|
42
31
|
writeUint32(writer, length);
|
|
43
32
|
}
|
|
44
|
-
addHandler('TySh', hasKey('text'),
|
|
33
|
+
addHandler('TySh', hasKey('text'), (reader, target, leftBytes) => {
|
|
45
34
|
if (readInt16(reader) !== 1)
|
|
46
|
-
throw new Error(
|
|
47
|
-
|
|
48
|
-
for (
|
|
35
|
+
throw new Error(`Invalid TySh version`);
|
|
36
|
+
const transform = [];
|
|
37
|
+
for (let i = 0; i < 6; i++)
|
|
49
38
|
transform.push(readFloat64(reader));
|
|
50
39
|
if (readInt16(reader) !== 50)
|
|
51
|
-
throw new Error(
|
|
52
|
-
|
|
40
|
+
throw new Error(`Invalid TySh text version`);
|
|
41
|
+
const text = readVersionAndDescriptor(reader);
|
|
53
42
|
// console.log(require('util').inspect(text, false, 99, false), 'utf8');
|
|
54
43
|
if (readInt16(reader) !== 1)
|
|
55
|
-
throw new Error(
|
|
56
|
-
|
|
44
|
+
throw new Error(`Invalid TySh warp version`);
|
|
45
|
+
const warp = readVersionAndDescriptor(reader);
|
|
57
46
|
// console.log(require('util').inspect(warp, false, 99, false), 'utf8');
|
|
58
47
|
target.text = {
|
|
59
|
-
transform
|
|
48
|
+
transform,
|
|
60
49
|
left: readFloat32(reader),
|
|
61
50
|
top: readFloat32(reader),
|
|
62
51
|
right: readFloat32(reader),
|
|
@@ -79,8 +68,8 @@ addHandler('TySh', hasKey('text'), function (reader, target, leftBytes) {
|
|
|
79
68
|
if (text.boundingBox)
|
|
80
69
|
target.text.boundingBox = descBoundsToBounds(text.boundingBox);
|
|
81
70
|
if (text.EngineData) {
|
|
82
|
-
|
|
83
|
-
|
|
71
|
+
const engineData = parseEngineData(text.EngineData);
|
|
72
|
+
const textData = decodeEngineData(engineData);
|
|
84
73
|
// console.log(require('util').inspect(engineData, false, 99, false), 'utf8');
|
|
85
74
|
// require('fs').writeFileSync(`layer-${target.name}.txt`, require('util').inspect(engineData, false, 99, false), 'utf8');
|
|
86
75
|
// const before = parseEngineData(text.EngineData);
|
|
@@ -88,17 +77,17 @@ addHandler('TySh', hasKey('text'), function (reader, target, leftBytes) {
|
|
|
88
77
|
// require('fs').writeFileSync('before.txt', require('util').inspect(before, false, 99, false), 'utf8');
|
|
89
78
|
// require('fs').writeFileSync('after.txt', require('util').inspect(after, false, 99, false), 'utf8');
|
|
90
79
|
// console.log(require('util').inspect(parseEngineData(text.EngineData), false, 99, true));
|
|
91
|
-
target.text =
|
|
80
|
+
target.text = Object.assign(Object.assign({}, target.text), textData);
|
|
92
81
|
// console.log(require('util').inspect(target.text, false, 99, true));
|
|
93
82
|
}
|
|
94
83
|
skipBytes(reader, leftBytes());
|
|
95
|
-
},
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
84
|
+
}, (writer, target) => {
|
|
85
|
+
const text = target.text;
|
|
86
|
+
const warp = text.warp || {};
|
|
87
|
+
const transform = text.transform || [1, 0, 0, 1, 0, 0];
|
|
88
|
+
const textDescriptor = Object.assign(Object.assign(Object.assign({ 'Txt ': (text.text || '').replace(/\r?\n/g, '\r'), textGridding: textGridding.encode(text.gridding), Ornt: Ornt.encode(text.orientation), AntA: Annt.encode(text.antiAlias) }, (text.bounds ? { bounds: boundsToDescBounds(text.bounds) } : {})), (text.boundingBox ? { boundingBox: boundsToDescBounds(text.boundingBox) } : {})), { TextIndex: text.index || 0, EngineData: serializeEngineData(encodeEngineData(text)) });
|
|
100
89
|
writeInt16(writer, 1); // version
|
|
101
|
-
for (
|
|
90
|
+
for (let i = 0; i < 6; i++) {
|
|
102
91
|
writeFloat64(writer, transform[i]);
|
|
103
92
|
}
|
|
104
93
|
writeInt16(writer, 50); // text version
|
|
@@ -112,48 +101,48 @@ addHandler('TySh', hasKey('text'), function (reader, target, leftBytes) {
|
|
|
112
101
|
// writeZeros(writer, 2);
|
|
113
102
|
});
|
|
114
103
|
// vector fills
|
|
115
|
-
addHandler('SoCo',
|
|
116
|
-
target.vectorFill.type === 'color'
|
|
117
|
-
|
|
104
|
+
addHandler('SoCo', target => target.vectorFill !== undefined && target.vectorStroke === undefined &&
|
|
105
|
+
target.vectorFill.type === 'color', (reader, target) => {
|
|
106
|
+
const descriptor = readVersionAndDescriptor(reader);
|
|
118
107
|
target.vectorFill = parseVectorContent(descriptor);
|
|
119
|
-
},
|
|
120
|
-
|
|
108
|
+
}, (writer, target) => {
|
|
109
|
+
const { descriptor } = serializeVectorContent(target.vectorFill);
|
|
121
110
|
writeVersionAndDescriptor(writer, '', 'null', descriptor);
|
|
122
111
|
});
|
|
123
|
-
addHandler('GdFl',
|
|
124
|
-
(target.vectorFill.type === 'solid' || target.vectorFill.type === 'noise')
|
|
125
|
-
|
|
112
|
+
addHandler('GdFl', target => target.vectorFill !== undefined && target.vectorStroke === undefined &&
|
|
113
|
+
(target.vectorFill.type === 'solid' || target.vectorFill.type === 'noise'), (reader, target, left) => {
|
|
114
|
+
const descriptor = readVersionAndDescriptor(reader);
|
|
126
115
|
target.vectorFill = parseVectorContent(descriptor);
|
|
127
116
|
skipBytes(reader, left());
|
|
128
|
-
},
|
|
129
|
-
|
|
117
|
+
}, (writer, target) => {
|
|
118
|
+
const { descriptor } = serializeVectorContent(target.vectorFill);
|
|
130
119
|
writeVersionAndDescriptor(writer, '', 'null', descriptor);
|
|
131
120
|
});
|
|
132
|
-
addHandler('PtFl',
|
|
133
|
-
target.vectorFill.type === 'pattern'
|
|
134
|
-
|
|
121
|
+
addHandler('PtFl', target => target.vectorFill !== undefined && target.vectorStroke === undefined &&
|
|
122
|
+
target.vectorFill.type === 'pattern', (reader, target) => {
|
|
123
|
+
const descriptor = readVersionAndDescriptor(reader);
|
|
135
124
|
target.vectorFill = parseVectorContent(descriptor);
|
|
136
|
-
},
|
|
137
|
-
|
|
125
|
+
}, (writer, target) => {
|
|
126
|
+
const { descriptor } = serializeVectorContent(target.vectorFill);
|
|
138
127
|
writeVersionAndDescriptor(writer, '', 'null', descriptor);
|
|
139
128
|
});
|
|
140
|
-
addHandler('vscg',
|
|
129
|
+
addHandler('vscg', target => target.vectorFill !== undefined && target.vectorStroke !== undefined, (reader, target, left) => {
|
|
141
130
|
readSignature(reader); // key
|
|
142
|
-
|
|
131
|
+
const desc = readVersionAndDescriptor(reader);
|
|
143
132
|
target.vectorFill = parseVectorContent(desc);
|
|
144
133
|
skipBytes(reader, left());
|
|
145
|
-
},
|
|
146
|
-
|
|
134
|
+
}, (writer, target) => {
|
|
135
|
+
const { descriptor, key } = serializeVectorContent(target.vectorFill);
|
|
147
136
|
writeSignature(writer, key);
|
|
148
137
|
writeVersionAndDescriptor(writer, '', 'null', descriptor);
|
|
149
138
|
});
|
|
150
139
|
export function readBezierKnot(reader, width, height) {
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
140
|
+
const y0 = readFixedPointPath32(reader) * height;
|
|
141
|
+
const x0 = readFixedPointPath32(reader) * width;
|
|
142
|
+
const y1 = readFixedPointPath32(reader) * height;
|
|
143
|
+
const x1 = readFixedPointPath32(reader) * width;
|
|
144
|
+
const y2 = readFixedPointPath32(reader) * height;
|
|
145
|
+
const x2 = readFixedPointPath32(reader) * width;
|
|
157
146
|
return [x0, y0, x1, y1, x2, y2];
|
|
158
147
|
}
|
|
159
148
|
function writeBezierKnot(writer, points, width, height) {
|
|
@@ -164,19 +153,19 @@ function writeBezierKnot(writer, points, width, height) {
|
|
|
164
153
|
writeFixedPointPath32(writer, points[5] / height); // y2
|
|
165
154
|
writeFixedPointPath32(writer, points[4] / width); // x2
|
|
166
155
|
}
|
|
167
|
-
export
|
|
156
|
+
export const booleanOperations = ['exclude', 'combine', 'subtract', 'intersect'];
|
|
168
157
|
export function readVectorMask(reader, vectorMask, width, height, size) {
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
158
|
+
const end = reader.offset + size;
|
|
159
|
+
const paths = vectorMask.paths;
|
|
160
|
+
let path = undefined;
|
|
172
161
|
while ((end - reader.offset) >= 26) {
|
|
173
|
-
|
|
162
|
+
const selector = readUint16(reader);
|
|
174
163
|
switch (selector) {
|
|
175
164
|
case 0: // Closed subpath length record
|
|
176
165
|
case 3: { // Open subpath length record
|
|
177
166
|
readUint16(reader); // count
|
|
178
|
-
|
|
179
|
-
|
|
167
|
+
const boolOp = readInt16(reader);
|
|
168
|
+
const flags = readUint16(reader); // bit 1 always 1 ?
|
|
180
169
|
skipBytes(reader, 18);
|
|
181
170
|
path = {
|
|
182
171
|
open: selector === 3,
|
|
@@ -199,13 +188,13 @@ export function readVectorMask(reader, vectorMask, width, height, size) {
|
|
|
199
188
|
break;
|
|
200
189
|
case 7: { // Clipboard record
|
|
201
190
|
// TODO: check if these need to be multiplied by document size
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
191
|
+
const top = readFixedPointPath32(reader);
|
|
192
|
+
const left = readFixedPointPath32(reader);
|
|
193
|
+
const bottom = readFixedPointPath32(reader);
|
|
194
|
+
const right = readFixedPointPath32(reader);
|
|
195
|
+
const resolution = readFixedPointPath32(reader);
|
|
207
196
|
skipBytes(reader, 4);
|
|
208
|
-
vectorMask.clipboard = { top
|
|
197
|
+
vectorMask.clipboard = { top, left, bottom, right, resolution };
|
|
209
198
|
break;
|
|
210
199
|
}
|
|
211
200
|
case 8: // Initial fill rule record
|
|
@@ -217,23 +206,21 @@ export function readVectorMask(reader, vectorMask, width, height, size) {
|
|
|
217
206
|
}
|
|
218
207
|
return paths;
|
|
219
208
|
}
|
|
220
|
-
addHandler('vmsk', hasKey('vectorMask'),
|
|
221
|
-
var width = _a.width, height = _a.height;
|
|
209
|
+
addHandler('vmsk', hasKey('vectorMask'), (reader, target, left, { width, height }) => {
|
|
222
210
|
if (readUint32(reader) !== 3)
|
|
223
211
|
throw new Error('Invalid vmsk version');
|
|
224
212
|
target.vectorMask = { paths: [] };
|
|
225
|
-
|
|
226
|
-
|
|
213
|
+
const vectorMask = target.vectorMask;
|
|
214
|
+
const flags = readUint32(reader);
|
|
227
215
|
vectorMask.invert = (flags & 1) !== 0;
|
|
228
216
|
vectorMask.notLink = (flags & 2) !== 0;
|
|
229
217
|
vectorMask.disable = (flags & 4) !== 0;
|
|
230
218
|
readVectorMask(reader, vectorMask, width, height, left());
|
|
231
219
|
// drawBezierPaths(vectorMask.paths, width, height, 'out.png');
|
|
232
220
|
skipBytes(reader, left());
|
|
233
|
-
},
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
var flags = (vectorMask.invert ? 1 : 0) |
|
|
221
|
+
}, (writer, target, { width, height }) => {
|
|
222
|
+
const vectorMask = target.vectorMask;
|
|
223
|
+
const flags = (vectorMask.invert ? 1 : 0) |
|
|
237
224
|
(vectorMask.notLink ? 2 : 0) |
|
|
238
225
|
(vectorMask.disable ? 4 : 0);
|
|
239
226
|
writeUint32(writer, 3); // version
|
|
@@ -241,7 +228,7 @@ addHandler('vmsk', hasKey('vectorMask'), function (reader, target, left, _a) {
|
|
|
241
228
|
// initial entry
|
|
242
229
|
writeUint16(writer, 6);
|
|
243
230
|
writeZeros(writer, 24);
|
|
244
|
-
|
|
231
|
+
const clipboard = vectorMask.clipboard;
|
|
245
232
|
if (clipboard) {
|
|
246
233
|
writeUint16(writer, 7);
|
|
247
234
|
writeFixedPointPath32(writer, clipboard.top);
|
|
@@ -254,17 +241,15 @@ addHandler('vmsk', hasKey('vectorMask'), function (reader, target, left, _a) {
|
|
|
254
241
|
writeUint16(writer, 8);
|
|
255
242
|
writeUint16(writer, vectorMask.fillStartsWithAllPixels ? 1 : 0);
|
|
256
243
|
writeZeros(writer, 22);
|
|
257
|
-
for (
|
|
258
|
-
var path = _b[_i];
|
|
244
|
+
for (const path of vectorMask.paths) {
|
|
259
245
|
writeUint16(writer, path.open ? 3 : 0);
|
|
260
246
|
writeUint16(writer, path.knots.length);
|
|
261
247
|
writeUint16(writer, path.operation ? booleanOperations.indexOf(path.operation) : -1); // -1 for undefined
|
|
262
248
|
writeUint16(writer, path.fillRule === 'non-zero' ? 2 : 1);
|
|
263
249
|
writeZeros(writer, 18); // TODO: these are sometimes non-zero
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
for (
|
|
267
|
-
var _e = _d[_c], linked = _e.linked, points = _e.points;
|
|
250
|
+
const linkedKnot = path.open ? 4 : 1;
|
|
251
|
+
const unlinkedKnot = path.open ? 5 : 2;
|
|
252
|
+
for (const { linked, points } of path.knots) {
|
|
268
253
|
writeUint16(writer, linked ? linkedKnot : unlinkedKnot);
|
|
269
254
|
writeBezierKnot(writer, points, width, height);
|
|
270
255
|
}
|
|
@@ -274,20 +259,19 @@ addHandler('vmsk', hasKey('vectorMask'), function (reader, target, left, _a) {
|
|
|
274
259
|
addHandlerAlias('vsms', 'vmsk');
|
|
275
260
|
// addHandlerAlias('vmsk', 'vsms');
|
|
276
261
|
addHandler('vowv', // something with vectors?
|
|
277
|
-
hasKey('vowv'),
|
|
262
|
+
hasKey('vowv'), (reader, target) => {
|
|
278
263
|
target.vowv = readUint32(reader); // always 2 ????
|
|
279
|
-
},
|
|
264
|
+
}, (writer, target) => {
|
|
280
265
|
writeUint32(writer, target.vowv);
|
|
281
266
|
});
|
|
282
|
-
addHandler('vogk', hasKey('vectorOrigination'),
|
|
267
|
+
addHandler('vogk', hasKey('vectorOrigination'), (reader, target, left) => {
|
|
283
268
|
if (readInt32(reader) !== 1)
|
|
284
|
-
throw new Error(
|
|
285
|
-
|
|
269
|
+
throw new Error(`Invalid vogk version`);
|
|
270
|
+
const desc = readVersionAndDescriptor(reader);
|
|
286
271
|
// console.log(require('util').inspect(desc, false, 99, true));
|
|
287
272
|
target.vectorOrigination = { keyDescriptorList: [] };
|
|
288
|
-
for (
|
|
289
|
-
|
|
290
|
-
var item = {};
|
|
273
|
+
for (const i of desc.keyDescriptorList) {
|
|
274
|
+
const item = {};
|
|
291
275
|
if (i.keyShapeInvalidated != null)
|
|
292
276
|
item.keyShapeInvalidated = i.keyShapeInvalidated;
|
|
293
277
|
if (i.keyOriginType != null)
|
|
@@ -302,7 +286,7 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
302
286
|
right: parseUnitsOrNumber(i.keyOriginShapeBBox.Rght),
|
|
303
287
|
};
|
|
304
288
|
}
|
|
305
|
-
|
|
289
|
+
const rectRadii = i.keyOriginRRectRadii;
|
|
306
290
|
if (rectRadii) {
|
|
307
291
|
item.keyOriginRRectRadii = {
|
|
308
292
|
topRight: parseUnits(rectRadii.topRight),
|
|
@@ -311,7 +295,7 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
311
295
|
bottomRight: parseUnits(rectRadii.bottomRight),
|
|
312
296
|
};
|
|
313
297
|
}
|
|
314
|
-
|
|
298
|
+
const corners = i.keyOriginBoxCorners;
|
|
315
299
|
if (corners) {
|
|
316
300
|
item.keyOriginBoxCorners = [
|
|
317
301
|
{ x: corners.rectangleCornerA.Hrzn, y: corners.rectangleCornerA.Vrtc },
|
|
@@ -320,26 +304,26 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
320
304
|
{ x: corners.rectangleCornerD.Hrzn, y: corners.rectangleCornerD.Vrtc },
|
|
321
305
|
];
|
|
322
306
|
}
|
|
323
|
-
|
|
307
|
+
const trnf = i.Trnf;
|
|
324
308
|
if (trnf) {
|
|
325
309
|
item.transform = [trnf.xx, trnf.xy, trnf.yx, trnf.yy, trnf.tx, trnf.ty];
|
|
326
310
|
}
|
|
327
311
|
target.vectorOrigination.keyDescriptorList.push(item);
|
|
328
312
|
}
|
|
329
313
|
skipBytes(reader, left());
|
|
330
|
-
},
|
|
314
|
+
}, (writer, target) => {
|
|
331
315
|
target;
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
for (
|
|
335
|
-
|
|
316
|
+
const orig = target.vectorOrigination;
|
|
317
|
+
const desc = { keyDescriptorList: [] };
|
|
318
|
+
for (let i = 0; i < orig.keyDescriptorList.length; i++) {
|
|
319
|
+
const item = orig.keyDescriptorList[i];
|
|
336
320
|
desc.keyDescriptorList.push({}); // we're adding keyOriginIndex at the end
|
|
337
|
-
|
|
321
|
+
const out = desc.keyDescriptorList[desc.keyDescriptorList.length - 1];
|
|
338
322
|
if (item.keyOriginType != null)
|
|
339
323
|
out.keyOriginType = item.keyOriginType;
|
|
340
324
|
if (item.keyOriginResolution != null)
|
|
341
325
|
out.keyOriginResolution = item.keyOriginResolution;
|
|
342
|
-
|
|
326
|
+
const radii = item.keyOriginRRectRadii;
|
|
343
327
|
if (radii) {
|
|
344
328
|
out.keyOriginRRectRadii = {
|
|
345
329
|
unitValueQuadVersion: 1,
|
|
@@ -349,7 +333,7 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
349
333
|
bottomRight: unitsValue(radii.bottomRight, 'bottomRight'),
|
|
350
334
|
};
|
|
351
335
|
}
|
|
352
|
-
|
|
336
|
+
const box = item.keyOriginShapeBoundingBox;
|
|
353
337
|
if (box) {
|
|
354
338
|
out.keyOriginShapeBBox = {
|
|
355
339
|
unitValueQuadVersion: 1,
|
|
@@ -359,7 +343,7 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
359
343
|
Rght: unitsValue(box.right, 'right'),
|
|
360
344
|
};
|
|
361
345
|
}
|
|
362
|
-
|
|
346
|
+
const corners = item.keyOriginBoxCorners;
|
|
363
347
|
if (corners && corners.length === 4) {
|
|
364
348
|
out.keyOriginBoxCorners = {
|
|
365
349
|
rectangleCornerA: { Hrzn: corners[0].x, Vrtc: corners[0].y },
|
|
@@ -368,7 +352,7 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
368
352
|
rectangleCornerD: { Hrzn: corners[3].x, Vrtc: corners[3].y },
|
|
369
353
|
};
|
|
370
354
|
}
|
|
371
|
-
|
|
355
|
+
const transform = item.transform;
|
|
372
356
|
if (transform && transform.length === 6) {
|
|
373
357
|
out.Trnf = {
|
|
374
358
|
xx: transform[0],
|
|
@@ -386,33 +370,33 @@ addHandler('vogk', hasKey('vectorOrigination'), function (reader, target, left)
|
|
|
386
370
|
writeInt32(writer, 1); // version
|
|
387
371
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
388
372
|
});
|
|
389
|
-
addHandler('lmfx',
|
|
390
|
-
|
|
373
|
+
addHandler('lmfx', target => target.effects !== undefined && hasMultiEffects(target.effects), (reader, target, left) => {
|
|
374
|
+
const version = readUint32(reader);
|
|
391
375
|
if (version !== 0)
|
|
392
376
|
throw new Error('Invalid lmfx version');
|
|
393
|
-
|
|
377
|
+
const desc = readVersionAndDescriptor(reader);
|
|
394
378
|
// console.log('READ', require('util').inspect(desc, false, 99, true));
|
|
395
379
|
// discard if read in 'lrFX' or 'lfx2' section
|
|
396
380
|
target.effects = parseEffects(desc, !!reader.logMissingFeatures);
|
|
397
381
|
skipBytes(reader, left());
|
|
398
|
-
},
|
|
399
|
-
|
|
382
|
+
}, (writer, target, _, options) => {
|
|
383
|
+
const desc = serializeEffects(target.effects, !!options.logMissingFeatures, true);
|
|
400
384
|
// console.log('WRITE', require('util').inspect(desc, false, 99, true));
|
|
401
385
|
writeUint32(writer, 0); // version
|
|
402
386
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
403
387
|
});
|
|
404
|
-
addHandler('lrFX', hasKey('effects'),
|
|
388
|
+
addHandler('lrFX', hasKey('effects'), (reader, target, left) => {
|
|
405
389
|
if (!target.effects)
|
|
406
390
|
target.effects = readEffects(reader);
|
|
407
391
|
skipBytes(reader, left());
|
|
408
|
-
},
|
|
392
|
+
}, (writer, target) => {
|
|
409
393
|
writeEffects(writer, target.effects);
|
|
410
394
|
});
|
|
411
|
-
addHandler('luni', hasKey('name'),
|
|
395
|
+
addHandler('luni', hasKey('name'), (reader, target, left) => {
|
|
412
396
|
if (left() > 4) {
|
|
413
|
-
|
|
414
|
-
if (left() >= (
|
|
415
|
-
target.name = readUnicodeStringWithLength(reader,
|
|
397
|
+
const length = readUint32(reader);
|
|
398
|
+
if (left() >= (length * 2)) {
|
|
399
|
+
target.name = readUnicodeStringWithLength(reader, length);
|
|
416
400
|
}
|
|
417
401
|
else {
|
|
418
402
|
if (reader.logDevFeatures)
|
|
@@ -424,22 +408,22 @@ addHandler('luni', hasKey('name'), function (reader, target, left) {
|
|
|
424
408
|
reader.log('empty luni section');
|
|
425
409
|
}
|
|
426
410
|
skipBytes(reader, left());
|
|
427
|
-
},
|
|
411
|
+
}, (writer, target) => {
|
|
428
412
|
writeUnicodeString(writer, target.name);
|
|
429
413
|
// writeUint16(writer, 0); // padding (but not extending string length)
|
|
430
414
|
});
|
|
431
|
-
addHandler('lnsr', hasKey('nameSource'),
|
|
432
|
-
addHandler('lyid', hasKey('id'),
|
|
415
|
+
addHandler('lnsr', hasKey('nameSource'), (reader, target) => target.nameSource = readSignature(reader), (writer, target) => writeSignature(writer, target.nameSource));
|
|
416
|
+
addHandler('lyid', hasKey('id'), (reader, target) => {
|
|
433
417
|
target.id = readUint32(reader);
|
|
434
|
-
},
|
|
435
|
-
|
|
418
|
+
}, (writer, target, _psd, options) => {
|
|
419
|
+
let id = target.id;
|
|
436
420
|
while (options.layerIds.has(id))
|
|
437
421
|
id += 100; // make sure we don't have duplicate layer ids
|
|
438
422
|
writeUint32(writer, id);
|
|
439
423
|
options.layerIds.add(id);
|
|
440
424
|
options.layerToId.set(target, id);
|
|
441
425
|
});
|
|
442
|
-
addHandler('lsct', hasKey('sectionDivider'),
|
|
426
|
+
addHandler('lsct', hasKey('sectionDivider'), (reader, target, left) => {
|
|
443
427
|
target.sectionDivider = { type: readUint32(reader) };
|
|
444
428
|
if (left()) {
|
|
445
429
|
checkSignature(reader, '8BIM');
|
|
@@ -448,7 +432,7 @@ addHandler('lsct', hasKey('sectionDivider'), function (reader, target, left) {
|
|
|
448
432
|
if (left()) {
|
|
449
433
|
target.sectionDivider.subType = readUint32(reader);
|
|
450
434
|
}
|
|
451
|
-
},
|
|
435
|
+
}, (writer, target) => {
|
|
452
436
|
writeUint32(writer, target.sectionDivider.type);
|
|
453
437
|
if (target.sectionDivider.key) {
|
|
454
438
|
writeSignature(writer, '8BIM');
|
|
@@ -461,36 +445,36 @@ addHandler('lsct', hasKey('sectionDivider'), function (reader, target, left) {
|
|
|
461
445
|
// it seems lsdk is used when there's a layer is nested more than 6 levels, but I don't know why?
|
|
462
446
|
// maybe some limitation of old version of PS?
|
|
463
447
|
addHandlerAlias('lsdk', 'lsct');
|
|
464
|
-
addHandler('clbl', hasKey('blendClippendElements'),
|
|
448
|
+
addHandler('clbl', hasKey('blendClippendElements'), (reader, target) => {
|
|
465
449
|
target.blendClippendElements = !!readUint8(reader);
|
|
466
450
|
skipBytes(reader, 3);
|
|
467
|
-
},
|
|
451
|
+
}, (writer, target) => {
|
|
468
452
|
writeUint8(writer, target.blendClippendElements ? 1 : 0);
|
|
469
453
|
writeZeros(writer, 3);
|
|
470
454
|
});
|
|
471
|
-
addHandler('infx', hasKey('blendInteriorElements'),
|
|
455
|
+
addHandler('infx', hasKey('blendInteriorElements'), (reader, target) => {
|
|
472
456
|
target.blendInteriorElements = !!readUint8(reader);
|
|
473
457
|
skipBytes(reader, 3);
|
|
474
|
-
},
|
|
458
|
+
}, (writer, target) => {
|
|
475
459
|
writeUint8(writer, target.blendInteriorElements ? 1 : 0);
|
|
476
460
|
writeZeros(writer, 3);
|
|
477
461
|
});
|
|
478
|
-
addHandler('knko', hasKey('knockout'),
|
|
462
|
+
addHandler('knko', hasKey('knockout'), (reader, target) => {
|
|
479
463
|
target.knockout = !!readUint8(reader);
|
|
480
464
|
skipBytes(reader, 3);
|
|
481
|
-
},
|
|
465
|
+
}, (writer, target) => {
|
|
482
466
|
writeUint8(writer, target.knockout ? 1 : 0);
|
|
483
467
|
writeZeros(writer, 3);
|
|
484
468
|
});
|
|
485
|
-
addHandler('lmgm', hasKey('layerMaskAsGlobalMask'),
|
|
469
|
+
addHandler('lmgm', hasKey('layerMaskAsGlobalMask'), (reader, target) => {
|
|
486
470
|
target.layerMaskAsGlobalMask = !!readUint8(reader);
|
|
487
471
|
skipBytes(reader, 3);
|
|
488
|
-
},
|
|
472
|
+
}, (writer, target) => {
|
|
489
473
|
writeUint8(writer, target.layerMaskAsGlobalMask ? 1 : 0);
|
|
490
474
|
writeZeros(writer, 3);
|
|
491
475
|
});
|
|
492
|
-
addHandler('lspf', hasKey('protected'),
|
|
493
|
-
|
|
476
|
+
addHandler('lspf', hasKey('protected'), (reader, target) => {
|
|
477
|
+
const flags = readUint32(reader);
|
|
494
478
|
target.protected = {
|
|
495
479
|
transparency: (flags & 0x01) !== 0,
|
|
496
480
|
composite: (flags & 0x02) !== 0,
|
|
@@ -498,45 +482,45 @@ addHandler('lspf', hasKey('protected'), function (reader, target) {
|
|
|
498
482
|
};
|
|
499
483
|
if (flags & 0x08)
|
|
500
484
|
target.protected.artboards = true;
|
|
501
|
-
},
|
|
502
|
-
|
|
485
|
+
}, (writer, target) => {
|
|
486
|
+
const flags = (target.protected.transparency ? 0x01 : 0) |
|
|
503
487
|
(target.protected.composite ? 0x02 : 0) |
|
|
504
488
|
(target.protected.position ? 0x04 : 0) |
|
|
505
489
|
(target.protected.artboards ? 0x08 : 0);
|
|
506
490
|
writeUint32(writer, flags);
|
|
507
491
|
});
|
|
508
|
-
addHandler('lclr', hasKey('layerColor'),
|
|
509
|
-
|
|
492
|
+
addHandler('lclr', hasKey('layerColor'), (reader, target) => {
|
|
493
|
+
const color = readUint16(reader);
|
|
510
494
|
skipBytes(reader, 6);
|
|
511
495
|
target.layerColor = layerColors[color];
|
|
512
|
-
},
|
|
513
|
-
|
|
496
|
+
}, (writer, target) => {
|
|
497
|
+
const index = layerColors.indexOf(target.layerColor);
|
|
514
498
|
writeUint16(writer, index === -1 ? 0 : index);
|
|
515
499
|
writeZeros(writer, 6);
|
|
516
500
|
});
|
|
517
501
|
addHandler('shmd', // Metadata setting
|
|
518
|
-
|
|
519
|
-
target
|
|
520
|
-
|
|
521
|
-
|
|
502
|
+
// Metadata setting
|
|
503
|
+
target => target.timestamp !== undefined || target.animationFrames !== undefined || target.animationFrameFlags !== undefined || target.timeline !== undefined || target.comps !== undefined, (reader, target, left) => {
|
|
504
|
+
const count = readUint32(reader);
|
|
505
|
+
for (let i = 0; i < count; i++) {
|
|
522
506
|
checkSignature(reader, '8BIM');
|
|
523
|
-
|
|
507
|
+
const key = readSignature(reader);
|
|
524
508
|
readUint8(reader); // copy
|
|
525
509
|
skipBytes(reader, 3);
|
|
526
|
-
readSection(reader, 1,
|
|
510
|
+
readSection(reader, 1, left => {
|
|
527
511
|
if (key === 'cust') {
|
|
528
|
-
|
|
512
|
+
const desc = readVersionAndDescriptor(reader);
|
|
529
513
|
// console.log('cust', target.name, require('util').inspect(desc, false, 99, true));
|
|
530
514
|
if (desc.layerTime !== undefined)
|
|
531
515
|
target.timestamp = desc.layerTime;
|
|
532
516
|
}
|
|
533
517
|
else if (key === 'mlst') {
|
|
534
|
-
|
|
518
|
+
const desc = readVersionAndDescriptor(reader);
|
|
535
519
|
// console.log('mlst', target.name, require('util').inspect(desc, false, 99, true));
|
|
536
520
|
target.animationFrames = [];
|
|
537
|
-
for (
|
|
538
|
-
|
|
539
|
-
|
|
521
|
+
for (let i = 0; i < desc.LaSt.length; i++) {
|
|
522
|
+
const f = desc.LaSt[i];
|
|
523
|
+
const frame = { frames: f.FrLs };
|
|
540
524
|
if (f.enab !== undefined)
|
|
541
525
|
frame.enable = f.enab;
|
|
542
526
|
if (f.Ofst)
|
|
@@ -553,8 +537,8 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
553
537
|
else if (key === 'mdyn') {
|
|
554
538
|
// frame flags
|
|
555
539
|
readUint16(reader); // unknown
|
|
556
|
-
|
|
557
|
-
|
|
540
|
+
const propagate = readUint8(reader);
|
|
541
|
+
const flags = readUint8(reader);
|
|
558
542
|
target.animationFrameFlags = {
|
|
559
543
|
propagateFrameOne: !propagate,
|
|
560
544
|
unifyLayerPosition: (flags & 1) !== 0,
|
|
@@ -563,10 +547,10 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
563
547
|
};
|
|
564
548
|
}
|
|
565
549
|
else if (key === 'tmln') {
|
|
566
|
-
|
|
567
|
-
|
|
550
|
+
const desc = readVersionAndDescriptor(reader);
|
|
551
|
+
const timeScope = desc.timeScope;
|
|
568
552
|
// console.log('tmln', target.name, target.id, require('util').inspect(desc, false, 99, true));
|
|
569
|
-
|
|
553
|
+
const timeline = {
|
|
570
554
|
start: frac(timeScope.Strt),
|
|
571
555
|
duration: frac(timeScope.duration),
|
|
572
556
|
inTime: frac(timeScope.inTime),
|
|
@@ -581,17 +565,16 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
581
565
|
// console.log('tmln:result', target.name, target.id, require('util').inspect(timeline, false, 99, true));
|
|
582
566
|
}
|
|
583
567
|
else if (key === 'cmls') {
|
|
584
|
-
|
|
568
|
+
const desc = readVersionAndDescriptor(reader);
|
|
585
569
|
// console.log('cmls', require('util').inspect(desc, false, 99, true));
|
|
586
570
|
target.comps = {
|
|
587
571
|
settings: [],
|
|
588
572
|
};
|
|
589
573
|
if (desc.origFXRefPoint)
|
|
590
574
|
target.comps.originalEffectsReferencePoint = { x: desc.origFXRefPoint.Hrzn, y: desc.origFXRefPoint.Vrtc };
|
|
591
|
-
for (
|
|
592
|
-
var item = _a[_i];
|
|
575
|
+
for (const item of desc.layerSettings) {
|
|
593
576
|
target.comps.settings.push({ compList: item.compList });
|
|
594
|
-
|
|
577
|
+
const t = target.comps.settings[target.comps.settings.length - 1];
|
|
595
578
|
if ('enab' in item)
|
|
596
579
|
t.enabled = item.enab;
|
|
597
580
|
if (item.Ofst)
|
|
@@ -601,7 +584,7 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
601
584
|
}
|
|
602
585
|
}
|
|
603
586
|
else if (key === 'extn') {
|
|
604
|
-
|
|
587
|
+
const desc = readVersionAndDescriptor(reader);
|
|
605
588
|
// console.log(require('util').inspect(desc, false, 99, true));
|
|
606
589
|
desc; // TODO: save this
|
|
607
590
|
reader.logMissingFeatures && reader.log('Unhandled "shmd" section key', key);
|
|
@@ -611,14 +594,11 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
611
594
|
}
|
|
612
595
|
skipBytes(reader, left());
|
|
613
596
|
});
|
|
614
|
-
};
|
|
615
|
-
for (var i = 0; i < count; i++) {
|
|
616
|
-
_loop_1(i);
|
|
617
597
|
}
|
|
618
598
|
skipBytes(reader, left());
|
|
619
|
-
},
|
|
620
|
-
|
|
621
|
-
|
|
599
|
+
}, (writer, target, _, options) => {
|
|
600
|
+
const { animationFrames, animationFrameFlags, timestamp, timeline, comps } = target;
|
|
601
|
+
let count = 0;
|
|
622
602
|
if (animationFrames)
|
|
623
603
|
count++;
|
|
624
604
|
if (animationFrameFlags)
|
|
@@ -635,15 +615,15 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
635
615
|
writeSignature(writer, 'mlst');
|
|
636
616
|
writeUint8(writer, 0); // copy (always false)
|
|
637
617
|
writeZeros(writer, 3);
|
|
638
|
-
writeSection(writer, 2,
|
|
618
|
+
writeSection(writer, 2, () => {
|
|
639
619
|
var _a;
|
|
640
|
-
|
|
620
|
+
const desc = {
|
|
641
621
|
LaID: (_a = target.id) !== null && _a !== void 0 ? _a : 0,
|
|
642
622
|
LaSt: [],
|
|
643
623
|
};
|
|
644
|
-
for (
|
|
645
|
-
|
|
646
|
-
|
|
624
|
+
for (let i = 0; i < animationFrames.length; i++) {
|
|
625
|
+
const f = animationFrames[i];
|
|
626
|
+
const frame = {};
|
|
647
627
|
if (f.enable !== undefined)
|
|
648
628
|
frame.enab = f.enable;
|
|
649
629
|
frame.FrLs = f.frames;
|
|
@@ -665,7 +645,7 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
665
645
|
writeSignature(writer, 'mdyn');
|
|
666
646
|
writeUint8(writer, 0); // copy (always false)
|
|
667
647
|
writeZeros(writer, 3);
|
|
668
|
-
writeSection(writer, 2,
|
|
648
|
+
writeSection(writer, 2, () => {
|
|
669
649
|
writeUint16(writer, 0); // unknown
|
|
670
650
|
writeUint8(writer, animationFrameFlags.propagateFrameOne ? 0x0 : 0xf);
|
|
671
651
|
writeUint8(writer, (animationFrameFlags.unifyLayerPosition ? 1 : 0) |
|
|
@@ -678,8 +658,8 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
678
658
|
writeSignature(writer, 'tmln');
|
|
679
659
|
writeUint8(writer, 0); // copy (always false)
|
|
680
660
|
writeZeros(writer, 3);
|
|
681
|
-
writeSection(writer, 2,
|
|
682
|
-
|
|
661
|
+
writeSection(writer, 2, () => {
|
|
662
|
+
const desc = {
|
|
683
663
|
Vrsn: 1,
|
|
684
664
|
timeScope: {
|
|
685
665
|
Vrsn: 1,
|
|
@@ -694,7 +674,7 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
694
674
|
if (timeline.tracks) {
|
|
695
675
|
desc.trackList = serializeTrackList(timeline.tracks);
|
|
696
676
|
}
|
|
697
|
-
|
|
677
|
+
const id = options.layerToId.get(target) || target.id;
|
|
698
678
|
if (!id)
|
|
699
679
|
throw new Error('You need to provide layer.id value whan writing document with animations');
|
|
700
680
|
desc.LyrI = id;
|
|
@@ -707,8 +687,8 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
707
687
|
writeSignature(writer, 'cust');
|
|
708
688
|
writeUint8(writer, 0); // copy (always false)
|
|
709
689
|
writeZeros(writer, 3);
|
|
710
|
-
writeSection(writer, 2,
|
|
711
|
-
|
|
690
|
+
writeSection(writer, 2, () => {
|
|
691
|
+
const desc = {
|
|
712
692
|
layerTime: timestamp,
|
|
713
693
|
};
|
|
714
694
|
writeVersionAndDescriptor(writer, '', 'metadata', desc);
|
|
@@ -719,19 +699,18 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
719
699
|
writeSignature(writer, 'cmls');
|
|
720
700
|
writeUint8(writer, 0); // copy (always false)
|
|
721
701
|
writeZeros(writer, 3);
|
|
722
|
-
writeSection(writer, 2,
|
|
723
|
-
|
|
702
|
+
writeSection(writer, 2, () => {
|
|
703
|
+
const id = options.layerToId.get(target) || target.id;
|
|
724
704
|
if (!id)
|
|
725
705
|
throw new Error('You need to provide layer.id value whan writing document with layer comps');
|
|
726
|
-
|
|
706
|
+
const desc = {};
|
|
727
707
|
if (comps.originalEffectsReferencePoint) {
|
|
728
708
|
desc.origFXRefPoint = { Hrzn: comps.originalEffectsReferencePoint.x, Vrtc: comps.originalEffectsReferencePoint.y };
|
|
729
709
|
}
|
|
730
710
|
desc.LyrI = id;
|
|
731
711
|
desc.layerSettings = [];
|
|
732
|
-
for (
|
|
733
|
-
|
|
734
|
-
var t = {};
|
|
712
|
+
for (const item of comps.settings) {
|
|
713
|
+
const t = {};
|
|
735
714
|
if (item.enabled !== undefined)
|
|
736
715
|
t.enab = item.enabled;
|
|
737
716
|
if (item.offset)
|
|
@@ -746,8 +725,8 @@ target) { return target.timestamp !== undefined || target.animationFrames !== un
|
|
|
746
725
|
}, true);
|
|
747
726
|
}
|
|
748
727
|
});
|
|
749
|
-
addHandler('PxSc',
|
|
750
|
-
|
|
728
|
+
addHandler('PxSc', () => false, (reader, target) => {
|
|
729
|
+
const desc = readVersionAndDescriptor(reader, true);
|
|
751
730
|
// console.log('PxSc', require('util').inspect(desc, false, 99, true));
|
|
752
731
|
if (desc.pixelSourceType === 1986285651) {
|
|
753
732
|
target.pixelSource = {
|
|
@@ -772,11 +751,11 @@ addHandler('PxSc', function () { return false; }, function (reader, target) {
|
|
|
772
751
|
};
|
|
773
752
|
}
|
|
774
753
|
else {
|
|
775
|
-
reader.log(
|
|
754
|
+
reader.log(`Unknown pixelSourceType`);
|
|
776
755
|
}
|
|
777
|
-
},
|
|
778
|
-
|
|
779
|
-
|
|
756
|
+
}, (writer, target) => {
|
|
757
|
+
const source = target.pixelSource;
|
|
758
|
+
const desc = {
|
|
780
759
|
_name: '',
|
|
781
760
|
_classID: 'PixelSource',
|
|
782
761
|
pixelSourceType: 1986285651,
|
|
@@ -786,7 +765,7 @@ addHandler('PxSc', function () { return false; }, function (reader, target) {
|
|
|
786
765
|
_name: '',
|
|
787
766
|
_classID: 'footageInterpretation',
|
|
788
767
|
Vrsn: 1,
|
|
789
|
-
interpretAlpha:
|
|
768
|
+
interpretAlpha: `alphaInterpretation.${source.interpretation.interpretAlpha}`,
|
|
790
769
|
profile: source.interpretation.profile,
|
|
791
770
|
},
|
|
792
771
|
frameReader: {
|
|
@@ -810,8 +789,8 @@ addHandler('PxSc', function () { return false; }, function (reader, target) {
|
|
|
810
789
|
};
|
|
811
790
|
writeVersionAndDescriptor(writer, '', 'PixelSource', desc);
|
|
812
791
|
});
|
|
813
|
-
addHandler('vstk', hasKey('vectorStroke'),
|
|
814
|
-
|
|
792
|
+
addHandler('vstk', hasKey('vectorStroke'), (reader, target, left) => {
|
|
793
|
+
const desc = readVersionAndDescriptor(reader);
|
|
815
794
|
// console.log(require('util').inspect(desc, false, 99, true));
|
|
816
795
|
target.vectorStroke = {
|
|
817
796
|
strokeEnabled: desc.strokeEnabled,
|
|
@@ -831,10 +810,10 @@ addHandler('vstk', hasKey('vectorStroke'), function (reader, target, left) {
|
|
|
831
810
|
resolution: desc.strokeStyleResolution,
|
|
832
811
|
};
|
|
833
812
|
skipBytes(reader, left());
|
|
834
|
-
},
|
|
813
|
+
}, (writer, target) => {
|
|
835
814
|
var _a, _b, _c;
|
|
836
|
-
|
|
837
|
-
|
|
815
|
+
const stroke = target.vectorStroke;
|
|
816
|
+
const desc = {
|
|
838
817
|
strokeStyleVersion: 2,
|
|
839
818
|
strokeEnabled: !!stroke.strokeEnabled,
|
|
840
819
|
fillEnabled: !!stroke.fillEnabled,
|
|
@@ -855,9 +834,9 @@ addHandler('vstk', hasKey('vectorStroke'), function (reader, target, left) {
|
|
|
855
834
|
writeVersionAndDescriptor(writer, '', 'strokeStyle', desc);
|
|
856
835
|
});
|
|
857
836
|
addHandler('artb', // per-layer arboard info
|
|
858
|
-
hasKey('artboard'),
|
|
859
|
-
|
|
860
|
-
|
|
837
|
+
hasKey('artboard'), (reader, target, left) => {
|
|
838
|
+
const desc = readVersionAndDescriptor(reader);
|
|
839
|
+
const rect = desc.artboardRect;
|
|
861
840
|
target.artboard = {
|
|
862
841
|
rect: { top: rect['Top '], left: rect.Left, bottom: rect.Btom, right: rect.Rght },
|
|
863
842
|
guideIndices: desc.guideIndeces,
|
|
@@ -866,11 +845,11 @@ hasKey('artboard'), function (reader, target, left) {
|
|
|
866
845
|
backgroundType: desc.artboardBackgroundType,
|
|
867
846
|
};
|
|
868
847
|
skipBytes(reader, left());
|
|
869
|
-
},
|
|
848
|
+
}, (writer, target) => {
|
|
870
849
|
var _a;
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
850
|
+
const artboard = target.artboard;
|
|
851
|
+
const rect = artboard.rect;
|
|
852
|
+
const desc = {
|
|
874
853
|
artboardRect: { 'Top ': rect.top, Left: rect.left, Btom: rect.bottom, Rght: rect.right },
|
|
875
854
|
guideIndeces: artboard.guideIndices || [],
|
|
876
855
|
artboardPresetName: artboard.presetName || '',
|
|
@@ -879,11 +858,11 @@ hasKey('artboard'), function (reader, target, left) {
|
|
|
879
858
|
};
|
|
880
859
|
writeVersionAndDescriptor(writer, '', 'artboard', desc);
|
|
881
860
|
});
|
|
882
|
-
addHandler('sn2P', hasKey('usingAlignedRendering'),
|
|
883
|
-
|
|
861
|
+
addHandler('sn2P', hasKey('usingAlignedRendering'), (reader, target) => target.usingAlignedRendering = !!readUint32(reader), (writer, target) => writeUint32(writer, target.usingAlignedRendering ? 1 : 0));
|
|
862
|
+
const placedLayerTypes = ['unknown', 'vector', 'raster', 'image stack'];
|
|
884
863
|
function parseWarp(warp) {
|
|
885
864
|
var _a, _b, _c, _d, _e, _f;
|
|
886
|
-
|
|
865
|
+
const result = Object.assign(Object.assign({ style: warpStyle.decode(warp.warpStyle) }, (warp.warpValues ? { values: warp.warpValues } : { value: warp.warpValue || 0 })), { perspective: warp.warpPerspective || 0, perspectiveOther: warp.warpPerspectiveOther || 0, rotate: Ornt.decode(warp.warpRotate), bounds: warp.bounds && {
|
|
887
866
|
top: parseUnitsOrNumber(warp.bounds['Top ']),
|
|
888
867
|
left: parseUnitsOrNumber(warp.bounds.Left),
|
|
889
868
|
bottom: parseUnitsOrNumber(warp.bounds.Btom),
|
|
@@ -893,14 +872,14 @@ function parseWarp(warp) {
|
|
|
893
872
|
result.deformNumRows = warp.deformNumRows;
|
|
894
873
|
result.deformNumCols = warp.deformNumCols;
|
|
895
874
|
}
|
|
896
|
-
|
|
875
|
+
const envelopeWarp = warp.customEnvelopeWarp;
|
|
897
876
|
if (envelopeWarp) {
|
|
898
877
|
result.customEnvelopeWarp = {
|
|
899
878
|
meshPoints: [],
|
|
900
879
|
};
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
for (
|
|
880
|
+
const xs = ((_a = envelopeWarp.meshPoints.find(i => i.type === 'Hrzn')) === null || _a === void 0 ? void 0 : _a.values) || [];
|
|
881
|
+
const ys = ((_b = envelopeWarp.meshPoints.find(i => i.type === 'Vrtc')) === null || _b === void 0 ? void 0 : _b.values) || [];
|
|
882
|
+
for (let i = 0; i < xs.length; i++) {
|
|
904
883
|
result.customEnvelopeWarp.meshPoints.push({ x: xs[i], y: ys[i] });
|
|
905
884
|
}
|
|
906
885
|
if (envelopeWarp.quiltSliceX || envelopeWarp.quiltSliceY) {
|
|
@@ -916,8 +895,8 @@ function isQuiltWarp(warp) {
|
|
|
916
895
|
((_a = warp.customEnvelopeWarp) === null || _a === void 0 ? void 0 : _a.quiltSliceX) || ((_b = warp.customEnvelopeWarp) === null || _b === void 0 ? void 0 : _b.quiltSliceY);
|
|
917
896
|
}
|
|
918
897
|
function encodeWarp(warp) {
|
|
919
|
-
|
|
920
|
-
|
|
898
|
+
const bounds = warp.bounds;
|
|
899
|
+
const desc = Object.assign(Object.assign({ warpStyle: warpStyle.encode(warp.style) }, (warp.values ? { warpValues: warp.values } : { warpValue: warp.value || 0 })), { warpPerspective: warp.perspective || 0, warpPerspectiveOther: warp.perspectiveOther || 0, warpRotate: Ornt.encode(warp.rotate), bounds: /*1 ? { // testing
|
|
921
900
|
_classID: 'classFloatRect',
|
|
922
901
|
'Top ': bounds && bounds.top && bounds.top.value || 0,
|
|
923
902
|
Left: bounds && bounds.left && bounds.left.value || 0,
|
|
@@ -929,17 +908,17 @@ function encodeWarp(warp) {
|
|
|
929
908
|
Btom: unitsValue(bounds && bounds.bottom || { units: 'Pixels', value: 0 }, 'bounds.bottom'),
|
|
930
909
|
Rght: unitsValue(bounds && bounds.right || { units: 'Pixels', value: 0 }, 'bounds.right'),
|
|
931
910
|
}, uOrder: warp.uOrder || 0, vOrder: warp.vOrder || 0 });
|
|
932
|
-
|
|
911
|
+
const isQuilt = isQuiltWarp(warp);
|
|
933
912
|
if (isQuilt) {
|
|
934
|
-
|
|
913
|
+
const desc2 = desc;
|
|
935
914
|
desc2.deformNumRows = warp.deformNumRows || 0;
|
|
936
915
|
desc2.deformNumCols = warp.deformNumCols || 0;
|
|
937
916
|
}
|
|
938
|
-
|
|
917
|
+
const customEnvelopeWarp = warp.customEnvelopeWarp;
|
|
939
918
|
if (customEnvelopeWarp) {
|
|
940
|
-
|
|
919
|
+
const meshPoints = customEnvelopeWarp.meshPoints || [];
|
|
941
920
|
if (isQuilt) {
|
|
942
|
-
|
|
921
|
+
const desc2 = desc;
|
|
943
922
|
desc2.customEnvelopeWarp = {
|
|
944
923
|
_name: '',
|
|
945
924
|
_classID: 'customEnvelopeWarp',
|
|
@@ -952,8 +931,8 @@ function encodeWarp(warp) {
|
|
|
952
931
|
values: customEnvelopeWarp.quiltSliceY || [],
|
|
953
932
|
}],
|
|
954
933
|
meshPoints: [
|
|
955
|
-
{ type: 'Hrzn', values: meshPoints.map(
|
|
956
|
-
{ type: 'Vrtc', values: meshPoints.map(
|
|
934
|
+
{ type: 'Hrzn', values: meshPoints.map(p => p.x) },
|
|
935
|
+
{ type: 'Vrtc', values: meshPoints.map(p => p.y) },
|
|
957
936
|
],
|
|
958
937
|
};
|
|
959
938
|
}
|
|
@@ -962,46 +941,46 @@ function encodeWarp(warp) {
|
|
|
962
941
|
_name: '',
|
|
963
942
|
_classID: 'customEnvelopeWarp',
|
|
964
943
|
meshPoints: [
|
|
965
|
-
{ type: 'Hrzn', values: meshPoints.map(
|
|
966
|
-
{ type: 'Vrtc', values: meshPoints.map(
|
|
944
|
+
{ type: 'Hrzn', values: meshPoints.map(p => p.x) },
|
|
945
|
+
{ type: 'Vrtc', values: meshPoints.map(p => p.y) },
|
|
967
946
|
],
|
|
968
947
|
};
|
|
969
948
|
}
|
|
970
949
|
}
|
|
971
950
|
return desc;
|
|
972
951
|
}
|
|
973
|
-
addHandler('PlLd', hasKey('placedLayer'),
|
|
952
|
+
addHandler('PlLd', hasKey('placedLayer'), (reader, target, left) => {
|
|
974
953
|
if (readSignature(reader) !== 'plcL')
|
|
975
|
-
throw new Error(
|
|
954
|
+
throw new Error(`Invalid PlLd signature`);
|
|
976
955
|
if (readInt32(reader) !== 3)
|
|
977
|
-
throw new Error(
|
|
978
|
-
|
|
979
|
-
|
|
980
|
-
|
|
956
|
+
throw new Error(`Invalid PlLd version`);
|
|
957
|
+
const id = readPascalString(reader, 1);
|
|
958
|
+
const pageNumber = readInt32(reader);
|
|
959
|
+
const totalPages = readInt32(reader); // TODO: check how this works ?
|
|
981
960
|
readInt32(reader); // anitAliasPolicy 16
|
|
982
|
-
|
|
961
|
+
const placedLayerType = readInt32(reader); // 0 = unknown, 1 = vector, 2 = raster, 3 = image stack
|
|
983
962
|
if (!placedLayerTypes[placedLayerType])
|
|
984
963
|
throw new Error('Invalid PlLd type');
|
|
985
|
-
|
|
986
|
-
for (
|
|
964
|
+
const transform = [];
|
|
965
|
+
for (let i = 0; i < 8; i++)
|
|
987
966
|
transform.push(readFloat64(reader)); // x, y of 4 corners of the transform
|
|
988
|
-
|
|
967
|
+
const warpVersion = readInt32(reader);
|
|
989
968
|
if (warpVersion !== 0)
|
|
990
|
-
throw new Error(
|
|
991
|
-
|
|
969
|
+
throw new Error(`Invalid Warp version ${warpVersion}`);
|
|
970
|
+
const warp = readVersionAndDescriptor(reader);
|
|
992
971
|
target.placedLayer = target.placedLayer || {
|
|
993
|
-
id
|
|
972
|
+
id,
|
|
994
973
|
type: placedLayerTypes[placedLayerType],
|
|
995
|
-
pageNumber
|
|
996
|
-
totalPages
|
|
997
|
-
transform
|
|
974
|
+
pageNumber,
|
|
975
|
+
totalPages,
|
|
976
|
+
transform,
|
|
998
977
|
warp: parseWarp(warp),
|
|
999
978
|
};
|
|
1000
979
|
// console.log('PlLd warp', require('util').inspect(warp, false, 99, true));
|
|
1001
980
|
// console.log('PlLd', require('util').inspect(target.placedLayer, false, 99, true));
|
|
1002
981
|
skipBytes(reader, left());
|
|
1003
|
-
},
|
|
1004
|
-
|
|
982
|
+
}, (writer, target) => {
|
|
983
|
+
const placed = target.placedLayer;
|
|
1005
984
|
writeSignature(writer, 'plcL');
|
|
1006
985
|
writeInt32(writer, 3); // version
|
|
1007
986
|
if (!placed.id || typeof placed.id !== 'string' || !/^[0-9a-f]{8}-([0-9a-f]{4}-){3}[0-9a-f]{12}$/.test(placed.id)) {
|
|
@@ -1014,12 +993,12 @@ addHandler('PlLd', hasKey('placedLayer'), function (reader, target, left) {
|
|
|
1014
993
|
if (placedLayerTypes.indexOf(placed.type) === -1)
|
|
1015
994
|
throw new Error('Invalid placedLayer type');
|
|
1016
995
|
writeInt32(writer, placedLayerTypes.indexOf(placed.type));
|
|
1017
|
-
for (
|
|
996
|
+
for (let i = 0; i < 8; i++)
|
|
1018
997
|
writeFloat64(writer, placed.transform[i]);
|
|
1019
998
|
writeInt32(writer, 0); // warp version
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
999
|
+
const warp = getWarpFromPlacedLayer(placed);
|
|
1000
|
+
const isQuilt = isQuiltWarp(warp);
|
|
1001
|
+
const type = isQuilt ? 'quiltWarp' : 'warp';
|
|
1023
1002
|
writeVersionAndDescriptor(writer, '', type, encodeWarp(warp), type);
|
|
1024
1003
|
});
|
|
1025
1004
|
function uint8ToFloat32(array) {
|
|
@@ -1032,15 +1011,15 @@ function toUint8(array) {
|
|
|
1032
1011
|
return new Uint8Array(array.buffer, array.byteOffset, array.byteLength);
|
|
1033
1012
|
}
|
|
1034
1013
|
function arrayToPoints(array) {
|
|
1035
|
-
|
|
1036
|
-
for (
|
|
1014
|
+
const points = [];
|
|
1015
|
+
for (let i = 0; i < array.length; i += 2) {
|
|
1037
1016
|
points.push({ x: array[i], y: array[i + 1] });
|
|
1038
1017
|
}
|
|
1039
1018
|
return points;
|
|
1040
1019
|
}
|
|
1041
1020
|
function pointsToArray(points) {
|
|
1042
|
-
|
|
1043
|
-
for (
|
|
1021
|
+
const array = [];
|
|
1022
|
+
for (let i = 0; i < points.length; i++) {
|
|
1044
1023
|
array.push(points[i].x, points[i].y);
|
|
1045
1024
|
}
|
|
1046
1025
|
return array;
|
|
@@ -1063,7 +1042,7 @@ function pointToHrznVrtc(point) {
|
|
|
1063
1042
|
};
|
|
1064
1043
|
}
|
|
1065
1044
|
function parseFilterFXItem(f, options) {
|
|
1066
|
-
|
|
1045
|
+
const base = {
|
|
1067
1046
|
name: f['Nm '],
|
|
1068
1047
|
opacity: parsePercent(f.blendOptions.Opct),
|
|
1069
1048
|
blendMode: BlnM.decode(f.blendOptions['Md ']),
|
|
@@ -1074,36 +1053,36 @@ function parseFilterFXItem(f, options) {
|
|
|
1074
1053
|
};
|
|
1075
1054
|
if ('Fltr' in f) {
|
|
1076
1055
|
switch (f.Fltr._classID) {
|
|
1077
|
-
case 'boxblur': return
|
|
1056
|
+
case 'boxblur': return Object.assign(Object.assign({}, base), { type: 'box blur', filter: {
|
|
1078
1057
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1079
1058
|
} });
|
|
1080
|
-
case 'GsnB': return
|
|
1059
|
+
case 'GsnB': return Object.assign(Object.assign({}, base), { type: 'gaussian blur', filter: {
|
|
1081
1060
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1082
1061
|
} });
|
|
1083
|
-
case 'MtnB': return
|
|
1062
|
+
case 'MtnB': return Object.assign(Object.assign({}, base), { type: 'motion blur', filter: {
|
|
1084
1063
|
angle: f.Fltr.Angl,
|
|
1085
1064
|
distance: parseUnits(f.Fltr.Dstn),
|
|
1086
1065
|
} });
|
|
1087
|
-
case 'RdlB': return
|
|
1066
|
+
case 'RdlB': return Object.assign(Object.assign({}, base), { type: 'radial blur', filter: {
|
|
1088
1067
|
amount: f.Fltr.Amnt,
|
|
1089
1068
|
method: BlrM.decode(f.Fltr.BlrM),
|
|
1090
1069
|
quality: BlrQ.decode(f.Fltr.BlrQ),
|
|
1091
1070
|
} });
|
|
1092
|
-
case 'shapeBlur': return
|
|
1071
|
+
case 'shapeBlur': return Object.assign(Object.assign({}, base), { type: 'shape blur', filter: {
|
|
1093
1072
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1094
1073
|
customShape: { name: f.Fltr.customShape['Nm '], id: f.Fltr.customShape.Idnt },
|
|
1095
1074
|
} });
|
|
1096
|
-
case 'SmrB': return
|
|
1075
|
+
case 'SmrB': return Object.assign(Object.assign({}, base), { type: 'smart blur', filter: {
|
|
1097
1076
|
radius: f.Fltr['Rds '],
|
|
1098
1077
|
threshold: f.Fltr.Thsh,
|
|
1099
1078
|
quality: SmBQ.decode(f.Fltr.SmBQ),
|
|
1100
1079
|
mode: SmBM.decode(f.Fltr.SmBM),
|
|
1101
1080
|
} });
|
|
1102
|
-
case 'surfaceBlur': return
|
|
1081
|
+
case 'surfaceBlur': return Object.assign(Object.assign({}, base), { type: 'surface blur', filter: {
|
|
1103
1082
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1104
1083
|
threshold: f.Fltr.Thsh,
|
|
1105
1084
|
} });
|
|
1106
|
-
case 'Dspl': return
|
|
1085
|
+
case 'Dspl': return Object.assign(Object.assign({}, base), { type: 'displace', filter: {
|
|
1107
1086
|
horizontalScale: f.Fltr.HrzS,
|
|
1108
1087
|
verticalScale: f.Fltr.VrtS,
|
|
1109
1088
|
displacementMap: DspM.decode(f.Fltr.DspM),
|
|
@@ -1113,30 +1092,30 @@ function parseFilterFXItem(f, options) {
|
|
|
1113
1092
|
path: f.Fltr.DspF.path, // TODO: this is decoded incorrectly ???
|
|
1114
1093
|
},
|
|
1115
1094
|
} });
|
|
1116
|
-
case 'Pnch': return
|
|
1095
|
+
case 'Pnch': return Object.assign(Object.assign({}, base), { type: 'pinch', filter: {
|
|
1117
1096
|
amount: f.Fltr.Amnt,
|
|
1118
1097
|
} });
|
|
1119
|
-
case 'Plr ': return
|
|
1098
|
+
case 'Plr ': return Object.assign(Object.assign({}, base), { type: 'polar coordinates', filter: {
|
|
1120
1099
|
conversion: Cnvr.decode(f.Fltr.Cnvr),
|
|
1121
1100
|
} });
|
|
1122
|
-
case 'Rple': return
|
|
1101
|
+
case 'Rple': return Object.assign(Object.assign({}, base), { type: 'ripple', filter: {
|
|
1123
1102
|
amount: f.Fltr.Amnt,
|
|
1124
1103
|
size: RplS.decode(f.Fltr.RplS),
|
|
1125
1104
|
} });
|
|
1126
|
-
case 'Shr ': return
|
|
1127
|
-
shearPoints: f.Fltr.ShrP.map(
|
|
1105
|
+
case 'Shr ': return Object.assign(Object.assign({}, base), { type: 'shear', filter: {
|
|
1106
|
+
shearPoints: f.Fltr.ShrP.map(p => ({ x: p.Hrzn, y: p.Vrtc })),
|
|
1128
1107
|
shearStart: f.Fltr.ShrS,
|
|
1129
1108
|
shearEnd: f.Fltr.ShrE,
|
|
1130
1109
|
undefinedAreas: UndA.decode(f.Fltr.UndA),
|
|
1131
1110
|
} });
|
|
1132
|
-
case 'Sphr': return
|
|
1111
|
+
case 'Sphr': return Object.assign(Object.assign({}, base), { type: 'spherize', filter: {
|
|
1133
1112
|
amount: f.Fltr.Amnt,
|
|
1134
1113
|
mode: SphM.decode(f.Fltr.SphM),
|
|
1135
1114
|
} });
|
|
1136
|
-
case 'Twrl': return
|
|
1115
|
+
case 'Twrl': return Object.assign(Object.assign({}, base), { type: 'twirl', filter: {
|
|
1137
1116
|
angle: f.Fltr.Angl,
|
|
1138
1117
|
} });
|
|
1139
|
-
case 'Wave': return
|
|
1118
|
+
case 'Wave': return Object.assign(Object.assign({}, base), { type: 'wave', filter: {
|
|
1140
1119
|
numberOfGenerators: f.Fltr.NmbG,
|
|
1141
1120
|
type: Wvtp.decode(f.Fltr.Wvtp),
|
|
1142
1121
|
wavelength: { min: f.Fltr.WLMn, max: f.Fltr.WLMx },
|
|
@@ -1145,70 +1124,70 @@ function parseFilterFXItem(f, options) {
|
|
|
1145
1124
|
randomSeed: f.Fltr.RndS,
|
|
1146
1125
|
undefinedAreas: UndA.decode(f.Fltr.UndA),
|
|
1147
1126
|
} });
|
|
1148
|
-
case 'ZgZg': return
|
|
1127
|
+
case 'ZgZg': return Object.assign(Object.assign({}, base), { type: 'zigzag', filter: {
|
|
1149
1128
|
amount: f.Fltr.Amnt,
|
|
1150
1129
|
ridges: f.Fltr.NmbR,
|
|
1151
1130
|
style: ZZTy.decode(f.Fltr.ZZTy),
|
|
1152
1131
|
} });
|
|
1153
|
-
case 'AdNs': return
|
|
1132
|
+
case 'AdNs': return Object.assign(Object.assign({}, base), { type: 'add noise', filter: {
|
|
1154
1133
|
amount: parsePercent(f.Fltr.Nose),
|
|
1155
1134
|
distribution: Dstr.decode(f.Fltr.Dstr),
|
|
1156
1135
|
monochromatic: f.Fltr.Mnch,
|
|
1157
1136
|
randomSeed: f.Fltr.FlRs,
|
|
1158
1137
|
} });
|
|
1159
|
-
case 'DstS': return
|
|
1138
|
+
case 'DstS': return Object.assign(Object.assign({}, base), { type: 'dust and scratches', filter: {
|
|
1160
1139
|
radius: f.Fltr['Rds '],
|
|
1161
1140
|
threshold: f.Fltr.Thsh,
|
|
1162
1141
|
} });
|
|
1163
|
-
case 'Mdn ': return
|
|
1142
|
+
case 'Mdn ': return Object.assign(Object.assign({}, base), { type: 'median', filter: {
|
|
1164
1143
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1165
1144
|
} });
|
|
1166
|
-
case 'denoise': return
|
|
1145
|
+
case 'denoise': return Object.assign(Object.assign({}, base), { type: 'reduce noise', filter: {
|
|
1167
1146
|
preset: f.Fltr.preset,
|
|
1168
1147
|
removeJpegArtifact: f.Fltr.removeJPEGArtifact,
|
|
1169
1148
|
reduceColorNoise: parsePercent(f.Fltr.ClNs),
|
|
1170
1149
|
sharpenDetails: parsePercent(f.Fltr.Shrp),
|
|
1171
|
-
channelDenoise: f.Fltr.channelDenoise.map(
|
|
1150
|
+
channelDenoise: f.Fltr.channelDenoise.map(c => (Object.assign({ channels: c.Chnl.map(Chnl.decode), amount: c.Amnt }, (c.EdgF ? { preserveDetails: c.EdgF } : {})))),
|
|
1172
1151
|
} });
|
|
1173
|
-
case 'ClrH': return
|
|
1152
|
+
case 'ClrH': return Object.assign(Object.assign({}, base), { type: 'color halftone', filter: {
|
|
1174
1153
|
radius: f.Fltr['Rds '],
|
|
1175
1154
|
angle1: f.Fltr.Ang1,
|
|
1176
1155
|
angle2: f.Fltr.Ang2,
|
|
1177
1156
|
angle3: f.Fltr.Ang3,
|
|
1178
1157
|
angle4: f.Fltr.Ang4,
|
|
1179
1158
|
} });
|
|
1180
|
-
case 'Crst': return
|
|
1159
|
+
case 'Crst': return Object.assign(Object.assign({}, base), { type: 'crystallize', filter: {
|
|
1181
1160
|
cellSize: f.Fltr.ClSz,
|
|
1182
1161
|
randomSeed: f.Fltr.FlRs,
|
|
1183
1162
|
} });
|
|
1184
|
-
case 'Mztn': return
|
|
1163
|
+
case 'Mztn': return Object.assign(Object.assign({}, base), { type: 'mezzotint', filter: {
|
|
1185
1164
|
type: MztT.decode(f.Fltr.MztT),
|
|
1186
1165
|
randomSeed: f.Fltr.FlRs,
|
|
1187
1166
|
} });
|
|
1188
|
-
case 'Msc ': return
|
|
1167
|
+
case 'Msc ': return Object.assign(Object.assign({}, base), { type: 'mosaic', filter: {
|
|
1189
1168
|
cellSize: parseUnits(f.Fltr.ClSz),
|
|
1190
1169
|
} });
|
|
1191
|
-
case 'Pntl': return
|
|
1170
|
+
case 'Pntl': return Object.assign(Object.assign({}, base), { type: 'pointillize', filter: {
|
|
1192
1171
|
cellSize: f.Fltr.ClSz,
|
|
1193
1172
|
randomSeed: f.Fltr.FlRs,
|
|
1194
1173
|
} });
|
|
1195
|
-
case 'Clds': return
|
|
1174
|
+
case 'Clds': return Object.assign(Object.assign({}, base), { type: 'clouds', filter: {
|
|
1196
1175
|
randomSeed: f.Fltr.FlRs,
|
|
1197
1176
|
} });
|
|
1198
|
-
case 'DfrC': return
|
|
1177
|
+
case 'DfrC': return Object.assign(Object.assign({}, base), { type: 'difference clouds', filter: {
|
|
1199
1178
|
randomSeed: f.Fltr.FlRs,
|
|
1200
1179
|
} });
|
|
1201
|
-
case 'Fbrs': return
|
|
1180
|
+
case 'Fbrs': return Object.assign(Object.assign({}, base), { type: 'fibers', filter: {
|
|
1202
1181
|
variance: f.Fltr.Vrnc,
|
|
1203
1182
|
strength: f.Fltr.Strg,
|
|
1204
1183
|
randomSeed: f.Fltr.RndS,
|
|
1205
1184
|
} });
|
|
1206
|
-
case 'LnsF': return
|
|
1185
|
+
case 'LnsF': return Object.assign(Object.assign({}, base), { type: 'lens flare', filter: {
|
|
1207
1186
|
brightness: f.Fltr.Brgh,
|
|
1208
1187
|
position: { x: f.Fltr.FlrC.Hrzn, y: f.Fltr.FlrC.Vrtc },
|
|
1209
1188
|
lensType: Lns.decode(f.Fltr['Lns ']),
|
|
1210
1189
|
} });
|
|
1211
|
-
case 'smartSharpen': return
|
|
1190
|
+
case 'smartSharpen': return Object.assign(Object.assign({}, base), { type: 'smart sharpen', filter: {
|
|
1212
1191
|
amount: parsePercent(f.Fltr.Amnt),
|
|
1213
1192
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1214
1193
|
threshold: f.Fltr.Thsh,
|
|
@@ -1227,21 +1206,21 @@ function parseFilterFXItem(f, options) {
|
|
|
1227
1206
|
radius: f.Fltr.hglM['Rds '],
|
|
1228
1207
|
},
|
|
1229
1208
|
} });
|
|
1230
|
-
case 'UnsM': return
|
|
1209
|
+
case 'UnsM': return Object.assign(Object.assign({}, base), { type: 'unsharp mask', filter: {
|
|
1231
1210
|
amount: parsePercent(f.Fltr.Amnt),
|
|
1232
1211
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1233
1212
|
threshold: f.Fltr.Thsh,
|
|
1234
1213
|
} });
|
|
1235
|
-
case 'Dfs ': return
|
|
1214
|
+
case 'Dfs ': return Object.assign(Object.assign({}, base), { type: 'diffuse', filter: {
|
|
1236
1215
|
mode: DfsM.decode(f.Fltr['Md ']),
|
|
1237
1216
|
randomSeed: f.Fltr.FlRs,
|
|
1238
1217
|
} });
|
|
1239
|
-
case 'Embs': return
|
|
1218
|
+
case 'Embs': return Object.assign(Object.assign({}, base), { type: 'emboss', filter: {
|
|
1240
1219
|
angle: f.Fltr.Angl,
|
|
1241
1220
|
height: f.Fltr.Hght,
|
|
1242
1221
|
amount: f.Fltr.Amnt,
|
|
1243
1222
|
} });
|
|
1244
|
-
case 'Extr': return
|
|
1223
|
+
case 'Extr': return Object.assign(Object.assign({}, base), { type: 'extrude', filter: {
|
|
1245
1224
|
type: ExtT.decode(f.Fltr.ExtT),
|
|
1246
1225
|
size: f.Fltr.ExtS,
|
|
1247
1226
|
depth: f.Fltr.ExtD,
|
|
@@ -1250,44 +1229,44 @@ function parseFilterFXItem(f, options) {
|
|
|
1250
1229
|
solidFrontFaces: f.Fltr.ExtF,
|
|
1251
1230
|
maskIncompleteBlocks: f.Fltr.ExtM,
|
|
1252
1231
|
} });
|
|
1253
|
-
case 'Tls ': return
|
|
1232
|
+
case 'Tls ': return Object.assign(Object.assign({}, base), { type: 'tiles', filter: {
|
|
1254
1233
|
numberOfTiles: f.Fltr.TlNm,
|
|
1255
1234
|
maximumOffset: f.Fltr.TlOf,
|
|
1256
1235
|
fillEmptyAreaWith: FlCl.decode(f.Fltr.FlCl),
|
|
1257
1236
|
randomSeed: f.Fltr.FlRs,
|
|
1258
1237
|
} });
|
|
1259
|
-
case 'TrcC': return
|
|
1238
|
+
case 'TrcC': return Object.assign(Object.assign({}, base), { type: 'trace contour', filter: {
|
|
1260
1239
|
level: f.Fltr['Lvl '],
|
|
1261
1240
|
edge: CntE.decode(f.Fltr['Edg ']),
|
|
1262
1241
|
} });
|
|
1263
|
-
case 'Wnd ': return
|
|
1242
|
+
case 'Wnd ': return Object.assign(Object.assign({}, base), { type: 'wind', filter: {
|
|
1264
1243
|
method: WndM.decode(f.Fltr.WndM),
|
|
1265
1244
|
direction: Drct.decode(f.Fltr.Drct),
|
|
1266
1245
|
} });
|
|
1267
|
-
case 'Dntr': return
|
|
1246
|
+
case 'Dntr': return Object.assign(Object.assign({}, base), { type: 'de-interlace', filter: {
|
|
1268
1247
|
eliminate: IntE.decode(f.Fltr.IntE),
|
|
1269
1248
|
newFieldsBy: IntC.decode(f.Fltr.IntC),
|
|
1270
1249
|
} });
|
|
1271
|
-
case 'Cstm': return
|
|
1250
|
+
case 'Cstm': return Object.assign(Object.assign({}, base), { type: 'custom', filter: {
|
|
1272
1251
|
scale: f.Fltr['Scl '],
|
|
1273
1252
|
offset: f.Fltr.Ofst,
|
|
1274
1253
|
matrix: f.Fltr.Mtrx,
|
|
1275
1254
|
} });
|
|
1276
|
-
case 'HghP': return
|
|
1255
|
+
case 'HghP': return Object.assign(Object.assign({}, base), { type: 'high pass', filter: {
|
|
1277
1256
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1278
1257
|
} });
|
|
1279
|
-
case 'Mxm ': return
|
|
1258
|
+
case 'Mxm ': return Object.assign(Object.assign({}, base), { type: 'maximum', filter: {
|
|
1280
1259
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1281
1260
|
} });
|
|
1282
|
-
case 'Mnm ': return
|
|
1261
|
+
case 'Mnm ': return Object.assign(Object.assign({}, base), { type: 'minimum', filter: {
|
|
1283
1262
|
radius: parseUnits(f.Fltr['Rds ']),
|
|
1284
1263
|
} });
|
|
1285
|
-
case 'Ofst': return
|
|
1264
|
+
case 'Ofst': return Object.assign(Object.assign({}, base), { type: 'offset', filter: {
|
|
1286
1265
|
horizontal: f.Fltr.Hrzn,
|
|
1287
1266
|
vertical: f.Fltr.Vrtc,
|
|
1288
1267
|
undefinedAreas: FlMd.decode(f.Fltr['Fl ']),
|
|
1289
1268
|
} });
|
|
1290
|
-
case 'rigidTransform': return
|
|
1269
|
+
case 'rigidTransform': return Object.assign(Object.assign({}, base), { type: 'puppet', filter: {
|
|
1291
1270
|
rigidType: f.Fltr.rigidType,
|
|
1292
1271
|
bounds: [
|
|
1293
1272
|
{ x: f.Fltr.PuX0, y: f.Fltr.PuY0, },
|
|
@@ -1295,7 +1274,7 @@ function parseFilterFXItem(f, options) {
|
|
|
1295
1274
|
{ x: f.Fltr.PuX2, y: f.Fltr.PuY2, },
|
|
1296
1275
|
{ x: f.Fltr.PuX3, y: f.Fltr.PuY3, },
|
|
1297
1276
|
],
|
|
1298
|
-
puppetShapeList: f.Fltr.puppetShapeList.map(
|
|
1277
|
+
puppetShapeList: f.Fltr.puppetShapeList.map(p => ({
|
|
1299
1278
|
rigidType: p.rigidType,
|
|
1300
1279
|
// TODO: VrsM
|
|
1301
1280
|
// TODO: VrsN
|
|
@@ -1315,41 +1294,41 @@ function parseFilterFXItem(f, options) {
|
|
|
1315
1294
|
meshRigidity: p.meshRigidity,
|
|
1316
1295
|
imageResolution: p.imageResolution,
|
|
1317
1296
|
meshBoundaryPath: {
|
|
1318
|
-
pathComponents: p.meshBoundaryPath.pathComponents.map(
|
|
1297
|
+
pathComponents: p.meshBoundaryPath.pathComponents.map(c => ({
|
|
1319
1298
|
shapeOperation: c.shapeOperation.split('.')[1],
|
|
1320
|
-
paths: c.SbpL.map(
|
|
1299
|
+
paths: c.SbpL.map(t => ({
|
|
1321
1300
|
closed: t.Clsp,
|
|
1322
|
-
points: t['Pts '].map(
|
|
1301
|
+
points: t['Pts '].map(pt => ({
|
|
1323
1302
|
anchor: hrznVrtcToPoint(pt.Anch),
|
|
1324
1303
|
forward: hrznVrtcToPoint(pt['Fwd ']),
|
|
1325
1304
|
backward: hrznVrtcToPoint(pt['Bwd ']),
|
|
1326
1305
|
smooth: pt.Smoo,
|
|
1327
|
-
})
|
|
1328
|
-
})
|
|
1329
|
-
})
|
|
1306
|
+
})),
|
|
1307
|
+
})),
|
|
1308
|
+
})),
|
|
1330
1309
|
},
|
|
1331
|
-
})
|
|
1310
|
+
})),
|
|
1332
1311
|
} });
|
|
1333
1312
|
case 'PbPl': {
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
for (
|
|
1337
|
-
if (!Flrt[
|
|
1313
|
+
const parameters = [];
|
|
1314
|
+
const Flrt = f.Fltr;
|
|
1315
|
+
for (let i = 0; i < fromAtoZ.length; i++) {
|
|
1316
|
+
if (!Flrt[`PN${fromAtoZ[i]}a`])
|
|
1338
1317
|
break;
|
|
1339
|
-
for (
|
|
1340
|
-
if (!Flrt[
|
|
1318
|
+
for (let j = 0; j < fromAtoZ.length; j++) {
|
|
1319
|
+
if (!Flrt[`PN${fromAtoZ[i]}${fromAtoZ[j]}`])
|
|
1341
1320
|
break;
|
|
1342
1321
|
parameters.push({
|
|
1343
|
-
name: Flrt[
|
|
1344
|
-
value: Flrt[
|
|
1322
|
+
name: Flrt[`PN${fromAtoZ[i]}${fromAtoZ[j]}`],
|
|
1323
|
+
value: Flrt[`PF${fromAtoZ[i]}${fromAtoZ[j]}`]
|
|
1345
1324
|
});
|
|
1346
1325
|
}
|
|
1347
1326
|
}
|
|
1348
|
-
return
|
|
1327
|
+
return Object.assign(Object.assign({}, base), { type: 'oil paint plugin', filter: {
|
|
1349
1328
|
name: f.Fltr.KnNm,
|
|
1350
1329
|
gpu: f.Fltr.GpuY,
|
|
1351
1330
|
lighting: f.Fltr.LIWy,
|
|
1352
|
-
parameters
|
|
1331
|
+
parameters,
|
|
1353
1332
|
} });
|
|
1354
1333
|
}
|
|
1355
1334
|
// case 2089: return {
|
|
@@ -1364,11 +1343,11 @@ function parseFilterFXItem(f, options) {
|
|
|
1364
1343
|
// imageY: f.Fltr.imgY,
|
|
1365
1344
|
// },
|
|
1366
1345
|
// };
|
|
1367
|
-
case 'HsbP': return
|
|
1346
|
+
case 'HsbP': return Object.assign(Object.assign({}, base), { type: 'hsb/hsl', filter: {
|
|
1368
1347
|
inputMode: ClrS.decode(f.Fltr.Inpt),
|
|
1369
1348
|
rowOrder: ClrS.decode(f.Fltr.Otpt),
|
|
1370
1349
|
} });
|
|
1371
|
-
case 'oilPaint': return
|
|
1350
|
+
case 'oilPaint': return Object.assign(Object.assign({}, base), { type: 'oil paint', filter: {
|
|
1372
1351
|
lightingOn: f.Fltr.lightingOn,
|
|
1373
1352
|
stylization: f.Fltr.stylization,
|
|
1374
1353
|
cleanliness: f.Fltr.cleanliness,
|
|
@@ -1379,30 +1358,30 @@ function parseFilterFXItem(f, options) {
|
|
|
1379
1358
|
} });
|
|
1380
1359
|
case 'LqFy':
|
|
1381
1360
|
{
|
|
1382
|
-
return
|
|
1361
|
+
return Object.assign(Object.assign({}, base), { type: 'liquify', filter: {
|
|
1383
1362
|
liquifyMesh: f.Fltr.LqMe,
|
|
1384
1363
|
} });
|
|
1385
1364
|
}
|
|
1386
1365
|
;
|
|
1387
1366
|
case 'perspectiveWarpTransform':
|
|
1388
1367
|
{
|
|
1389
|
-
return
|
|
1368
|
+
return Object.assign(Object.assign({}, base), { type: 'perspective warp', filter: {
|
|
1390
1369
|
vertices: f.Fltr.vertices.map(hrznVrtcToPoint),
|
|
1391
1370
|
warpedVertices: f.Fltr.warpedVertices.map(hrznVrtcToPoint),
|
|
1392
|
-
quads: f.Fltr.quads.map(
|
|
1371
|
+
quads: f.Fltr.quads.map(q => q.indices),
|
|
1393
1372
|
} });
|
|
1394
1373
|
}
|
|
1395
1374
|
;
|
|
1396
1375
|
case 'Crvs':
|
|
1397
1376
|
{
|
|
1398
|
-
return
|
|
1399
|
-
adjustments: f.Fltr.Adjs.map(
|
|
1400
|
-
|
|
1377
|
+
return Object.assign(Object.assign({}, base), { type: 'curves', filter: Object.assign({ presetKind: presetKindType.decode(f.Fltr.presetKind) }, (f.Fltr.Adjs ? {
|
|
1378
|
+
adjustments: f.Fltr.Adjs.map(a => {
|
|
1379
|
+
const channels = a.Chnl.map(Chnl.decode);
|
|
1401
1380
|
if (a['Crv ']) {
|
|
1402
1381
|
return {
|
|
1403
|
-
channels
|
|
1404
|
-
curve: a['Crv '].map(
|
|
1405
|
-
|
|
1382
|
+
channels,
|
|
1383
|
+
curve: a['Crv '].map(c => {
|
|
1384
|
+
const point = { x: c.Hrzn, y: c.Vrtc };
|
|
1406
1385
|
if (c.Cnty)
|
|
1407
1386
|
point.curved = true;
|
|
1408
1387
|
return point;
|
|
@@ -1410,10 +1389,10 @@ function parseFilterFXItem(f, options) {
|
|
|
1410
1389
|
};
|
|
1411
1390
|
}
|
|
1412
1391
|
else if (a.Mpng) {
|
|
1413
|
-
return { channels
|
|
1392
|
+
return { channels, values: a.Mpng };
|
|
1414
1393
|
}
|
|
1415
1394
|
else {
|
|
1416
|
-
throw new Error(
|
|
1395
|
+
throw new Error(`Unknown curve adjustment`);
|
|
1417
1396
|
}
|
|
1418
1397
|
})
|
|
1419
1398
|
} : {})) });
|
|
@@ -1421,7 +1400,7 @@ function parseFilterFXItem(f, options) {
|
|
|
1421
1400
|
;
|
|
1422
1401
|
case 'BrgC':
|
|
1423
1402
|
{
|
|
1424
|
-
return
|
|
1403
|
+
return Object.assign(Object.assign({}, base), { type: 'brightness/contrast', filter: {
|
|
1425
1404
|
brightness: f.Fltr.Brgh,
|
|
1426
1405
|
contrast: f.Fltr.Cntr,
|
|
1427
1406
|
useLegacy: !!f.Fltr.useLegacy,
|
|
@@ -1431,30 +1410,30 @@ function parseFilterFXItem(f, options) {
|
|
|
1431
1410
|
default:
|
|
1432
1411
|
if (options.throwForMissingFeatures) {
|
|
1433
1412
|
// console.log('FILTER', require('util').inspect(f, false, 99, true));
|
|
1434
|
-
throw new Error(
|
|
1413
|
+
throw new Error(`Unknown filter classId: ${f.Fltr._classID}`);
|
|
1435
1414
|
}
|
|
1436
1415
|
return undefined;
|
|
1437
1416
|
}
|
|
1438
1417
|
}
|
|
1439
1418
|
else {
|
|
1440
1419
|
switch (f.filterID) {
|
|
1441
|
-
case 1098281575: return
|
|
1442
|
-
case 1114403360: return
|
|
1443
|
-
case 1114403405: return
|
|
1444
|
-
case 1148416099: return
|
|
1445
|
-
case 1180922912: return
|
|
1446
|
-
case 1181902701: return
|
|
1447
|
-
case 1399353968: return
|
|
1448
|
-
case 1399353925: return
|
|
1449
|
-
case 1399353933: return
|
|
1450
|
-
case 1181639749: return
|
|
1451
|
-
case 1399616122: return
|
|
1452
|
-
case 1314149187: return
|
|
1453
|
-
case 1231976050: return
|
|
1420
|
+
case 1098281575: return Object.assign(Object.assign({}, base), { type: 'average' });
|
|
1421
|
+
case 1114403360: return Object.assign(Object.assign({}, base), { type: 'blur' });
|
|
1422
|
+
case 1114403405: return Object.assign(Object.assign({}, base), { type: 'blur more' });
|
|
1423
|
+
case 1148416099: return Object.assign(Object.assign({}, base), { type: 'despeckle' });
|
|
1424
|
+
case 1180922912: return Object.assign(Object.assign({}, base), { type: 'facet' });
|
|
1425
|
+
case 1181902701: return Object.assign(Object.assign({}, base), { type: 'fragment' });
|
|
1426
|
+
case 1399353968: return Object.assign(Object.assign({}, base), { type: 'sharpen' });
|
|
1427
|
+
case 1399353925: return Object.assign(Object.assign({}, base), { type: 'sharpen edges' });
|
|
1428
|
+
case 1399353933: return Object.assign(Object.assign({}, base), { type: 'sharpen more' });
|
|
1429
|
+
case 1181639749: return Object.assign(Object.assign({}, base), { type: 'find edges' });
|
|
1430
|
+
case 1399616122: return Object.assign(Object.assign({}, base), { type: 'solarize' });
|
|
1431
|
+
case 1314149187: return Object.assign(Object.assign({}, base), { type: 'ntsc colors' });
|
|
1432
|
+
case 1231976050: return Object.assign(Object.assign({}, base), { type: 'invert' });
|
|
1454
1433
|
default:
|
|
1455
1434
|
if (options.throwForMissingFeatures) {
|
|
1456
1435
|
// console.log('FILTER', require('util').inspect(f, false, 99, true));
|
|
1457
|
-
throw new Error(
|
|
1436
|
+
throw new Error(`Unknown filterID: ${f.filterID}`);
|
|
1458
1437
|
}
|
|
1459
1438
|
}
|
|
1460
1439
|
}
|
|
@@ -1466,14 +1445,14 @@ function parseFilterFX(desc, options) {
|
|
|
1466
1445
|
maskEnabled: desc.filterMaskEnable,
|
|
1467
1446
|
maskLinked: desc.filterMaskLinked,
|
|
1468
1447
|
maskExtendWithWhite: desc.filterMaskExtendWithWhite,
|
|
1469
|
-
list: desc.filterFXList.map(
|
|
1448
|
+
list: desc.filterFXList.map(x => parseFilterFXItem(x, options)).filter((x) => !!x),
|
|
1470
1449
|
};
|
|
1471
1450
|
}
|
|
1472
1451
|
function uvRadius(t) {
|
|
1473
1452
|
return unitsValue(t.radius, 'radius');
|
|
1474
1453
|
}
|
|
1475
1454
|
function serializeFilterFXItem(f) {
|
|
1476
|
-
|
|
1455
|
+
const base = {
|
|
1477
1456
|
_name: '',
|
|
1478
1457
|
_classID: 'filterFX',
|
|
1479
1458
|
'Nm ': f.name,
|
|
@@ -1489,34 +1468,34 @@ function serializeFilterFXItem(f) {
|
|
|
1489
1468
|
BckC: serializeColor(f.backgroundColor),
|
|
1490
1469
|
};
|
|
1491
1470
|
switch (f.type) {
|
|
1492
|
-
case 'average': return
|
|
1493
|
-
case 'blur': return
|
|
1494
|
-
case 'blur more': return
|
|
1495
|
-
case 'box blur': return
|
|
1471
|
+
case 'average': return Object.assign(Object.assign({}, base), { filterID: 1098281575 });
|
|
1472
|
+
case 'blur': return Object.assign(Object.assign({}, base), { filterID: 1114403360 });
|
|
1473
|
+
case 'blur more': return Object.assign(Object.assign({}, base), { filterID: 1114403405 });
|
|
1474
|
+
case 'box blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1496
1475
|
_name: 'Box Blur',
|
|
1497
1476
|
_classID: 'boxblur',
|
|
1498
1477
|
'Rds ': uvRadius(f.filter),
|
|
1499
1478
|
}, filterID: 697 });
|
|
1500
|
-
case 'gaussian blur': return
|
|
1479
|
+
case 'gaussian blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1501
1480
|
// _name: '高斯模糊', // Testing
|
|
1502
1481
|
_name: 'Gaussian Blur',
|
|
1503
1482
|
_classID: 'GsnB',
|
|
1504
1483
|
'Rds ': uvRadius(f.filter),
|
|
1505
1484
|
}, filterID: 1198747202 });
|
|
1506
|
-
case 'motion blur': return
|
|
1485
|
+
case 'motion blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1507
1486
|
_name: 'Motion Blur',
|
|
1508
1487
|
_classID: 'MtnB',
|
|
1509
1488
|
Angl: f.filter.angle,
|
|
1510
1489
|
Dstn: unitsValue(f.filter.distance, 'distance'),
|
|
1511
1490
|
}, filterID: 1299476034 });
|
|
1512
|
-
case 'radial blur': return
|
|
1491
|
+
case 'radial blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1513
1492
|
_name: 'Radial Blur',
|
|
1514
1493
|
_classID: 'RdlB',
|
|
1515
1494
|
Amnt: f.filter.amount,
|
|
1516
1495
|
BlrM: BlrM.encode(f.filter.method),
|
|
1517
1496
|
BlrQ: BlrQ.encode(f.filter.quality),
|
|
1518
1497
|
}, filterID: 1382313026 });
|
|
1519
|
-
case 'shape blur': return
|
|
1498
|
+
case 'shape blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1520
1499
|
_name: 'Shape Blur',
|
|
1521
1500
|
_classID: 'shapeBlur',
|
|
1522
1501
|
'Rds ': uvRadius(f.filter),
|
|
@@ -1527,7 +1506,7 @@ function serializeFilterFXItem(f) {
|
|
|
1527
1506
|
Idnt: f.filter.customShape.id,
|
|
1528
1507
|
}
|
|
1529
1508
|
}, filterID: 702 });
|
|
1530
|
-
case 'smart blur': return
|
|
1509
|
+
case 'smart blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1531
1510
|
_name: 'Smart Blur',
|
|
1532
1511
|
_classID: 'SmrB',
|
|
1533
1512
|
'Rds ': f.filter.radius,
|
|
@@ -1535,13 +1514,13 @@ function serializeFilterFXItem(f) {
|
|
|
1535
1514
|
SmBQ: SmBQ.encode(f.filter.quality),
|
|
1536
1515
|
SmBM: SmBM.encode(f.filter.mode),
|
|
1537
1516
|
}, filterID: 1399681602 });
|
|
1538
|
-
case 'surface blur': return
|
|
1517
|
+
case 'surface blur': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1539
1518
|
_name: 'Surface Blur',
|
|
1540
1519
|
_classID: 'surfaceBlur',
|
|
1541
1520
|
'Rds ': uvRadius(f.filter),
|
|
1542
1521
|
Thsh: f.filter.threshold,
|
|
1543
1522
|
}, filterID: 701 });
|
|
1544
|
-
case 'displace': return
|
|
1523
|
+
case 'displace': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1545
1524
|
_name: 'Displace',
|
|
1546
1525
|
_classID: 'Dspl',
|
|
1547
1526
|
HrzS: f.filter.horizontalScale,
|
|
@@ -1553,42 +1532,42 @@ function serializeFilterFXItem(f) {
|
|
|
1553
1532
|
path: f.filter.displacementFile.path,
|
|
1554
1533
|
},
|
|
1555
1534
|
}, filterID: 1148416108 });
|
|
1556
|
-
case 'pinch': return
|
|
1535
|
+
case 'pinch': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1557
1536
|
_name: 'Pinch',
|
|
1558
1537
|
_classID: 'Pnch',
|
|
1559
1538
|
Amnt: f.filter.amount,
|
|
1560
1539
|
}, filterID: 1349411688 });
|
|
1561
|
-
case 'polar coordinates': return
|
|
1540
|
+
case 'polar coordinates': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1562
1541
|
_name: 'Polar Coordinates',
|
|
1563
1542
|
_classID: 'Plr ',
|
|
1564
1543
|
Cnvr: Cnvr.encode(f.filter.conversion),
|
|
1565
1544
|
}, filterID: 1349284384 });
|
|
1566
|
-
case 'ripple': return
|
|
1545
|
+
case 'ripple': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1567
1546
|
_name: 'Ripple',
|
|
1568
1547
|
_classID: 'Rple',
|
|
1569
1548
|
Amnt: f.filter.amount,
|
|
1570
1549
|
RplS: RplS.encode(f.filter.size),
|
|
1571
1550
|
}, filterID: 1383099493 });
|
|
1572
|
-
case 'shear': return
|
|
1551
|
+
case 'shear': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1573
1552
|
_name: 'Shear',
|
|
1574
1553
|
_classID: 'Shr ',
|
|
1575
|
-
ShrP: f.filter.shearPoints.map(
|
|
1554
|
+
ShrP: f.filter.shearPoints.map(p => ({ _name: '', _classID: 'Pnt ', Hrzn: p.x, Vrtc: p.y })),
|
|
1576
1555
|
UndA: UndA.encode(f.filter.undefinedAreas),
|
|
1577
1556
|
ShrS: f.filter.shearStart,
|
|
1578
1557
|
ShrE: f.filter.shearEnd,
|
|
1579
1558
|
}, filterID: 1399353888 });
|
|
1580
|
-
case 'spherize': return
|
|
1559
|
+
case 'spherize': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1581
1560
|
_name: 'Spherize',
|
|
1582
1561
|
_classID: 'Sphr',
|
|
1583
1562
|
Amnt: f.filter.amount,
|
|
1584
1563
|
SphM: SphM.encode(f.filter.mode),
|
|
1585
1564
|
}, filterID: 1399875698 });
|
|
1586
|
-
case 'twirl': return
|
|
1565
|
+
case 'twirl': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1587
1566
|
_name: 'Twirl',
|
|
1588
1567
|
_classID: 'Twrl',
|
|
1589
1568
|
Angl: f.filter.angle,
|
|
1590
1569
|
}, filterID: 1417114220 });
|
|
1591
|
-
case 'wave': return
|
|
1570
|
+
case 'wave': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1592
1571
|
_name: 'Wave',
|
|
1593
1572
|
_classID: 'Wave',
|
|
1594
1573
|
Wvtp: Wvtp.encode(f.filter.type),
|
|
@@ -1602,14 +1581,14 @@ function serializeFilterFXItem(f) {
|
|
|
1602
1581
|
UndA: UndA.encode(f.filter.undefinedAreas),
|
|
1603
1582
|
RndS: f.filter.randomSeed,
|
|
1604
1583
|
}, filterID: 1466005093 });
|
|
1605
|
-
case 'zigzag': return
|
|
1584
|
+
case 'zigzag': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1606
1585
|
_name: 'ZigZag',
|
|
1607
1586
|
_classID: 'ZgZg',
|
|
1608
1587
|
Amnt: f.filter.amount,
|
|
1609
1588
|
NmbR: f.filter.ridges,
|
|
1610
1589
|
ZZTy: ZZTy.encode(f.filter.style),
|
|
1611
1590
|
}, filterID: 1516722791 });
|
|
1612
|
-
case 'add noise': return
|
|
1591
|
+
case 'add noise': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1613
1592
|
_name: 'Add Noise',
|
|
1614
1593
|
_classID: 'AdNs',
|
|
1615
1594
|
Dstr: Dstr.encode(f.filter.distribution),
|
|
@@ -1617,28 +1596,28 @@ function serializeFilterFXItem(f) {
|
|
|
1617
1596
|
Mnch: f.filter.monochromatic,
|
|
1618
1597
|
FlRs: f.filter.randomSeed,
|
|
1619
1598
|
}, filterID: 1097092723 });
|
|
1620
|
-
case 'despeckle': return
|
|
1621
|
-
case 'dust and scratches': return
|
|
1599
|
+
case 'despeckle': return Object.assign(Object.assign({}, base), { filterID: 1148416099 });
|
|
1600
|
+
case 'dust and scratches': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1622
1601
|
_name: 'Dust & Scratches',
|
|
1623
1602
|
_classID: 'DstS',
|
|
1624
1603
|
'Rds ': f.filter.radius,
|
|
1625
1604
|
Thsh: f.filter.threshold,
|
|
1626
1605
|
}, filterID: 1148417107 });
|
|
1627
|
-
case 'median': return
|
|
1606
|
+
case 'median': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1628
1607
|
_name: 'Median',
|
|
1629
1608
|
_classID: 'Mdn ',
|
|
1630
1609
|
'Rds ': uvRadius(f.filter),
|
|
1631
1610
|
}, filterID: 1298427424 });
|
|
1632
|
-
case 'reduce noise': return
|
|
1611
|
+
case 'reduce noise': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1633
1612
|
_name: 'Reduce Noise',
|
|
1634
1613
|
_classID: 'denoise',
|
|
1635
1614
|
ClNs: unitsPercentF(f.filter.reduceColorNoise),
|
|
1636
1615
|
Shrp: unitsPercentF(f.filter.sharpenDetails),
|
|
1637
1616
|
removeJPEGArtifact: f.filter.removeJpegArtifact,
|
|
1638
|
-
channelDenoise: f.filter.channelDenoise.map(
|
|
1617
|
+
channelDenoise: f.filter.channelDenoise.map(c => (Object.assign({ _name: '', _classID: 'channelDenoiseParams', Chnl: c.channels.map(i => Chnl.encode(i)), Amnt: c.amount }, (c.preserveDetails ? { EdgF: c.preserveDetails } : {})))),
|
|
1639
1618
|
preset: f.filter.preset,
|
|
1640
1619
|
}, filterID: 633 });
|
|
1641
|
-
case 'color halftone': return
|
|
1620
|
+
case 'color halftone': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1642
1621
|
_name: 'Color Halftone',
|
|
1643
1622
|
_classID: 'ClrH',
|
|
1644
1623
|
'Rds ': f.filter.radius,
|
|
@@ -1647,49 +1626,49 @@ function serializeFilterFXItem(f) {
|
|
|
1647
1626
|
Ang3: f.filter.angle3,
|
|
1648
1627
|
Ang4: f.filter.angle4,
|
|
1649
1628
|
}, filterID: 1131180616 });
|
|
1650
|
-
case 'crystallize': return
|
|
1629
|
+
case 'crystallize': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1651
1630
|
_name: 'Crystallize',
|
|
1652
1631
|
_classID: 'Crst',
|
|
1653
1632
|
ClSz: f.filter.cellSize,
|
|
1654
1633
|
FlRs: f.filter.randomSeed,
|
|
1655
1634
|
}, filterID: 1131574132 });
|
|
1656
|
-
case 'facet': return
|
|
1657
|
-
case 'fragment': return
|
|
1658
|
-
case 'mezzotint': return
|
|
1635
|
+
case 'facet': return Object.assign(Object.assign({}, base), { filterID: 1180922912 });
|
|
1636
|
+
case 'fragment': return Object.assign(Object.assign({}, base), { filterID: 1181902701 });
|
|
1637
|
+
case 'mezzotint': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1659
1638
|
_name: 'Mezzotint',
|
|
1660
1639
|
_classID: 'Mztn',
|
|
1661
1640
|
MztT: MztT.encode(f.filter.type),
|
|
1662
1641
|
FlRs: f.filter.randomSeed,
|
|
1663
1642
|
}, filterID: 1299870830 });
|
|
1664
|
-
case 'mosaic': return
|
|
1643
|
+
case 'mosaic': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1665
1644
|
_name: 'Mosaic',
|
|
1666
1645
|
_classID: 'Msc ',
|
|
1667
1646
|
ClSz: unitsValue(f.filter.cellSize, 'cellSize'),
|
|
1668
1647
|
}, filterID: 1299407648 });
|
|
1669
|
-
case 'pointillize': return
|
|
1648
|
+
case 'pointillize': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1670
1649
|
_name: 'Pointillize',
|
|
1671
1650
|
_classID: 'Pntl',
|
|
1672
1651
|
ClSz: f.filter.cellSize,
|
|
1673
1652
|
FlRs: f.filter.randomSeed,
|
|
1674
1653
|
}, filterID: 1349416044 });
|
|
1675
|
-
case 'clouds': return
|
|
1654
|
+
case 'clouds': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1676
1655
|
_name: 'Clouds',
|
|
1677
1656
|
_classID: 'Clds',
|
|
1678
1657
|
FlRs: f.filter.randomSeed,
|
|
1679
1658
|
}, filterID: 1131177075 });
|
|
1680
|
-
case 'difference clouds': return
|
|
1659
|
+
case 'difference clouds': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1681
1660
|
_name: 'Difference Clouds',
|
|
1682
1661
|
_classID: 'DfrC',
|
|
1683
1662
|
FlRs: f.filter.randomSeed,
|
|
1684
1663
|
}, filterID: 1147564611 });
|
|
1685
|
-
case 'fibers': return
|
|
1664
|
+
case 'fibers': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1686
1665
|
_name: 'Fibers',
|
|
1687
1666
|
_classID: 'Fbrs',
|
|
1688
1667
|
Vrnc: f.filter.variance,
|
|
1689
1668
|
Strg: f.filter.strength,
|
|
1690
1669
|
RndS: f.filter.randomSeed,
|
|
1691
1670
|
}, filterID: 1180856947 });
|
|
1692
|
-
case 'lens flare': return
|
|
1671
|
+
case 'lens flare': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1693
1672
|
_name: 'Lens Flare',
|
|
1694
1673
|
_classID: 'LnsF',
|
|
1695
1674
|
Brgh: f.filter.brightness,
|
|
@@ -1701,10 +1680,10 @@ function serializeFilterFXItem(f) {
|
|
|
1701
1680
|
},
|
|
1702
1681
|
'Lns ': Lns.encode(f.filter.lensType),
|
|
1703
1682
|
}, filterID: 1282306886 });
|
|
1704
|
-
case 'sharpen': return
|
|
1705
|
-
case 'sharpen edges': return
|
|
1706
|
-
case 'sharpen more': return
|
|
1707
|
-
case 'smart sharpen': return
|
|
1683
|
+
case 'sharpen': return Object.assign(Object.assign({}, base), { filterID: 1399353968 });
|
|
1684
|
+
case 'sharpen edges': return Object.assign(Object.assign({}, base), { filterID: 1399353925 });
|
|
1685
|
+
case 'sharpen more': return Object.assign(Object.assign({}, base), { filterID: 1399353933 });
|
|
1686
|
+
case 'smart sharpen': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1708
1687
|
_name: 'Smart Sharpen',
|
|
1709
1688
|
_classID: 'smartSharpen',
|
|
1710
1689
|
Amnt: unitsPercentF(f.filter.amount),
|
|
@@ -1729,27 +1708,27 @@ function serializeFilterFXItem(f) {
|
|
|
1729
1708
|
'Rds ': f.filter.highlight.radius,
|
|
1730
1709
|
},
|
|
1731
1710
|
}, filterID: 698 });
|
|
1732
|
-
case 'unsharp mask': return
|
|
1711
|
+
case 'unsharp mask': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1733
1712
|
_name: 'Unsharp Mask',
|
|
1734
1713
|
_classID: 'UnsM',
|
|
1735
1714
|
Amnt: unitsPercentF(f.filter.amount),
|
|
1736
1715
|
'Rds ': uvRadius(f.filter),
|
|
1737
1716
|
Thsh: f.filter.threshold,
|
|
1738
1717
|
}, filterID: 1433301837 });
|
|
1739
|
-
case 'diffuse': return
|
|
1718
|
+
case 'diffuse': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1740
1719
|
_name: 'Diffuse',
|
|
1741
1720
|
_classID: 'Dfs ',
|
|
1742
1721
|
'Md ': DfsM.encode(f.filter.mode),
|
|
1743
1722
|
FlRs: f.filter.randomSeed,
|
|
1744
1723
|
}, filterID: 1147564832 });
|
|
1745
|
-
case 'emboss': return
|
|
1724
|
+
case 'emboss': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1746
1725
|
_name: 'Emboss',
|
|
1747
1726
|
_classID: 'Embs',
|
|
1748
1727
|
Angl: f.filter.angle,
|
|
1749
1728
|
Hght: f.filter.height,
|
|
1750
1729
|
Amnt: f.filter.amount,
|
|
1751
1730
|
}, filterID: 1164796531 });
|
|
1752
|
-
case 'extrude': return
|
|
1731
|
+
case 'extrude': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1753
1732
|
_name: 'Extrude',
|
|
1754
1733
|
_classID: 'Extr',
|
|
1755
1734
|
ExtS: f.filter.size,
|
|
@@ -1760,9 +1739,9 @@ function serializeFilterFXItem(f) {
|
|
|
1760
1739
|
ExtR: ExtR.encode(f.filter.depthMode),
|
|
1761
1740
|
FlRs: f.filter.randomSeed,
|
|
1762
1741
|
}, filterID: 1165522034 });
|
|
1763
|
-
case 'find edges': return
|
|
1764
|
-
case 'solarize': return
|
|
1765
|
-
case 'tiles': return
|
|
1742
|
+
case 'find edges': return Object.assign(Object.assign({}, base), { filterID: 1181639749 });
|
|
1743
|
+
case 'solarize': return Object.assign(Object.assign({}, base), { filterID: 1399616122 });
|
|
1744
|
+
case 'tiles': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1766
1745
|
_name: 'Tiles',
|
|
1767
1746
|
_classID: 'Tls ',
|
|
1768
1747
|
TlNm: f.filter.numberOfTiles,
|
|
@@ -1770,61 +1749,61 @@ function serializeFilterFXItem(f) {
|
|
|
1770
1749
|
FlCl: FlCl.encode(f.filter.fillEmptyAreaWith),
|
|
1771
1750
|
FlRs: f.filter.randomSeed,
|
|
1772
1751
|
}, filterID: 1416393504 });
|
|
1773
|
-
case 'trace contour': return
|
|
1752
|
+
case 'trace contour': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1774
1753
|
_name: 'Trace Contour',
|
|
1775
1754
|
_classID: 'TrcC',
|
|
1776
1755
|
'Lvl ': f.filter.level,
|
|
1777
1756
|
'Edg ': CntE.encode(f.filter.edge),
|
|
1778
1757
|
}, filterID: 1416782659 });
|
|
1779
|
-
case 'wind': return
|
|
1758
|
+
case 'wind': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1780
1759
|
_name: 'Wind',
|
|
1781
1760
|
_classID: 'Wnd ',
|
|
1782
1761
|
WndM: WndM.encode(f.filter.method),
|
|
1783
1762
|
Drct: Drct.encode(f.filter.direction),
|
|
1784
1763
|
}, filterID: 1466852384 });
|
|
1785
|
-
case 'de-interlace': return
|
|
1764
|
+
case 'de-interlace': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1786
1765
|
_name: 'De-Interlace',
|
|
1787
1766
|
_classID: 'Dntr',
|
|
1788
1767
|
IntE: IntE.encode(f.filter.eliminate),
|
|
1789
1768
|
IntC: IntC.encode(f.filter.newFieldsBy),
|
|
1790
1769
|
}, filterID: 1148089458 });
|
|
1791
|
-
case 'ntsc colors': return
|
|
1792
|
-
case 'invert': return
|
|
1793
|
-
case 'custom': return
|
|
1770
|
+
case 'ntsc colors': return Object.assign(Object.assign({}, base), { filterID: 1314149187 });
|
|
1771
|
+
case 'invert': return Object.assign(Object.assign({}, base), { filterID: 1231976050 });
|
|
1772
|
+
case 'custom': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1794
1773
|
_name: 'Custom',
|
|
1795
1774
|
_classID: 'Cstm',
|
|
1796
1775
|
'Scl ': f.filter.scale,
|
|
1797
1776
|
Ofst: f.filter.offset,
|
|
1798
1777
|
Mtrx: f.filter.matrix,
|
|
1799
1778
|
}, filterID: 1131639917 });
|
|
1800
|
-
case 'high pass': return
|
|
1779
|
+
case 'high pass': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1801
1780
|
_name: 'High Pass',
|
|
1802
1781
|
_classID: 'HghP',
|
|
1803
1782
|
'Rds ': uvRadius(f.filter),
|
|
1804
1783
|
}, filterID: 1214736464 });
|
|
1805
|
-
case 'maximum': return
|
|
1784
|
+
case 'maximum': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1806
1785
|
_name: 'Maximum',
|
|
1807
1786
|
_classID: 'Mxm ',
|
|
1808
1787
|
'Rds ': uvRadius(f.filter),
|
|
1809
1788
|
}, filterID: 1299737888 });
|
|
1810
|
-
case 'minimum': return
|
|
1789
|
+
case 'minimum': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1811
1790
|
_name: 'Minimum',
|
|
1812
1791
|
_classID: 'Mnm ',
|
|
1813
1792
|
'Rds ': uvRadius(f.filter),
|
|
1814
1793
|
}, filterID: 1299082528 });
|
|
1815
|
-
case 'offset': return
|
|
1794
|
+
case 'offset': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1816
1795
|
_name: 'Offset',
|
|
1817
1796
|
_classID: 'Ofst',
|
|
1818
1797
|
Hrzn: f.filter.horizontal,
|
|
1819
1798
|
Vrtc: f.filter.vertical,
|
|
1820
1799
|
'Fl ': FlMd.encode(f.filter.undefinedAreas),
|
|
1821
1800
|
}, filterID: 1332114292 });
|
|
1822
|
-
case 'puppet': return
|
|
1801
|
+
case 'puppet': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1823
1802
|
_name: 'Rigid Transform',
|
|
1824
1803
|
_classID: 'rigidTransform',
|
|
1825
1804
|
'null': ['Ordn.Trgt'],
|
|
1826
1805
|
rigidType: f.filter.rigidType,
|
|
1827
|
-
puppetShapeList: f.filter.puppetShapeList.map(
|
|
1806
|
+
puppetShapeList: f.filter.puppetShapeList.map(p => ({
|
|
1828
1807
|
_name: '',
|
|
1829
1808
|
_classID: 'puppetShape',
|
|
1830
1809
|
rigidType: p.rigidType,
|
|
@@ -1847,27 +1826,27 @@ function serializeFilterFXItem(f) {
|
|
|
1847
1826
|
meshBoundaryPath: {
|
|
1848
1827
|
_name: '',
|
|
1849
1828
|
_classID: 'pathClass',
|
|
1850
|
-
pathComponents: p.meshBoundaryPath.pathComponents.map(
|
|
1829
|
+
pathComponents: p.meshBoundaryPath.pathComponents.map(c => ({
|
|
1851
1830
|
_name: '',
|
|
1852
1831
|
_classID: 'PaCm',
|
|
1853
|
-
shapeOperation:
|
|
1854
|
-
SbpL: c.paths.map(
|
|
1832
|
+
shapeOperation: `shapeOperation.${c.shapeOperation}`,
|
|
1833
|
+
SbpL: c.paths.map(path => ({
|
|
1855
1834
|
_name: '',
|
|
1856
1835
|
_classID: 'Sbpl',
|
|
1857
1836
|
Clsp: path.closed,
|
|
1858
|
-
'Pts ': path.points.map(
|
|
1837
|
+
'Pts ': path.points.map(pt => ({
|
|
1859
1838
|
_name: '',
|
|
1860
1839
|
_classID: 'Pthp',
|
|
1861
1840
|
Anch: pointToHrznVrtc(pt.anchor),
|
|
1862
1841
|
'Fwd ': pointToHrznVrtc(pt.forward),
|
|
1863
1842
|
'Bwd ': pointToHrznVrtc(pt.backward),
|
|
1864
1843
|
Smoo: pt.smooth,
|
|
1865
|
-
})
|
|
1866
|
-
})
|
|
1867
|
-
})
|
|
1844
|
+
})),
|
|
1845
|
+
})),
|
|
1846
|
+
})),
|
|
1868
1847
|
},
|
|
1869
1848
|
selectedPin: p.selectedPin,
|
|
1870
|
-
})
|
|
1849
|
+
})),
|
|
1871
1850
|
PuX0: f.filter.bounds[0].x,
|
|
1872
1851
|
PuX1: f.filter.bounds[1].x,
|
|
1873
1852
|
PuX2: f.filter.bounds[2].x,
|
|
@@ -1878,17 +1857,17 @@ function serializeFilterFXItem(f) {
|
|
|
1878
1857
|
PuY3: f.filter.bounds[3].y,
|
|
1879
1858
|
}, filterID: 991 });
|
|
1880
1859
|
case 'oil paint plugin': {
|
|
1881
|
-
|
|
1882
|
-
for (
|
|
1883
|
-
|
|
1884
|
-
|
|
1885
|
-
params[
|
|
1886
|
-
params[
|
|
1887
|
-
params[
|
|
1860
|
+
const params = {};
|
|
1861
|
+
for (let i = 0; i < f.filter.parameters.length; i++) {
|
|
1862
|
+
const { name, value } = f.filter.parameters[i];
|
|
1863
|
+
const suffix = `${fromAtoZ[Math.floor(i / fromAtoZ.length)]}${fromAtoZ[i % fromAtoZ.length]}`;
|
|
1864
|
+
params[`PN${suffix}`] = name;
|
|
1865
|
+
params[`PT${suffix}`] = 0;
|
|
1866
|
+
params[`PF${suffix}`] = value;
|
|
1888
1867
|
}
|
|
1889
|
-
return
|
|
1868
|
+
return Object.assign(Object.assign({}, base), { Fltr: Object.assign({ _name: 'Oil Paint Plugin', _classID: 'PbPl', KnNm: f.filter.name, GpuY: f.filter.gpu, LIWy: f.filter.lighting, FPth: '1' }, params), filterID: 1348620396 });
|
|
1890
1869
|
}
|
|
1891
|
-
case 'oil paint': return
|
|
1870
|
+
case 'oil paint': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1892
1871
|
_name: 'Oil Paint',
|
|
1893
1872
|
_classID: 'oilPaint',
|
|
1894
1873
|
lightingOn: f.filter.lightingOn,
|
|
@@ -1899,32 +1878,32 @@ function serializeFilterFXItem(f) {
|
|
|
1899
1878
|
LghD: f.filter.lightDirection,
|
|
1900
1879
|
specularity: f.filter.specularity,
|
|
1901
1880
|
}, filterID: 1122 });
|
|
1902
|
-
case 'liquify': return
|
|
1881
|
+
case 'liquify': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1903
1882
|
_name: 'Liquify',
|
|
1904
1883
|
_classID: 'LqFy',
|
|
1905
1884
|
LqMe: f.filter.liquifyMesh,
|
|
1906
1885
|
}, filterID: 1282492025 });
|
|
1907
|
-
case 'perspective warp': return
|
|
1886
|
+
case 'perspective warp': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1908
1887
|
_name: 'Perspective Warp',
|
|
1909
1888
|
_classID: 'perspectiveWarpTransform',
|
|
1910
1889
|
vertices: f.filter.vertices.map(pointToHrznVrtc),
|
|
1911
1890
|
warpedVertices: f.filter.warpedVertices.map(pointToHrznVrtc),
|
|
1912
|
-
quads: f.filter.quads.map(
|
|
1891
|
+
quads: f.filter.quads.map(indices => ({ indices })),
|
|
1913
1892
|
}, filterID: 442 });
|
|
1914
|
-
case 'curves': return
|
|
1915
|
-
Adjs: f.filter.adjustments.map(
|
|
1893
|
+
case 'curves': return Object.assign(Object.assign({}, base), { Fltr: Object.assign({ _name: 'Curves', _classID: 'Crvs', presetKind: presetKindType.encode(f.filter.presetKind) }, (f.filter.adjustments ? {
|
|
1894
|
+
Adjs: f.filter.adjustments.map(a => 'curve' in a ? {
|
|
1916
1895
|
_name: '',
|
|
1917
1896
|
_classID: 'CrvA',
|
|
1918
1897
|
Chnl: a.channels.map(Chnl.encode),
|
|
1919
|
-
'Crv ': a.curve.map(
|
|
1898
|
+
'Crv ': a.curve.map(c => (Object.assign({ _name: '', _classID: 'Pnt ', Hrzn: c.x, Vrtc: c.y }, (c.curved ? { Cnty: true } : {})))),
|
|
1920
1899
|
} : {
|
|
1921
1900
|
_name: '',
|
|
1922
1901
|
_classID: 'CrvA',
|
|
1923
1902
|
Chnl: a.channels.map(Chnl.encode),
|
|
1924
1903
|
Mpng: a.values,
|
|
1925
|
-
}
|
|
1904
|
+
})
|
|
1926
1905
|
} : {})), filterID: 1131574899 });
|
|
1927
|
-
case 'brightness/contrast': return
|
|
1906
|
+
case 'brightness/contrast': return Object.assign(Object.assign({}, base), { Fltr: {
|
|
1928
1907
|
_name: 'Brightness/Contrast',
|
|
1929
1908
|
_classID: 'BrgC',
|
|
1930
1909
|
Brgh: f.filter.brightness,
|
|
@@ -1934,7 +1913,7 @@ function serializeFilterFXItem(f) {
|
|
|
1934
1913
|
// case 'hsb/hsl': return {
|
|
1935
1914
|
// TODO: ...
|
|
1936
1915
|
// };
|
|
1937
|
-
default: throw new Error(
|
|
1916
|
+
default: throw new Error(`Unknow filter type: ${f.type}`);
|
|
1938
1917
|
}
|
|
1939
1918
|
}
|
|
1940
1919
|
// let t: any;
|
|
@@ -1943,10 +1922,10 @@ function getWarpFromPlacedLayer(placed) {
|
|
|
1943
1922
|
return placed.warp;
|
|
1944
1923
|
if (!placed.width || !placed.height)
|
|
1945
1924
|
throw new Error('You must provide width and height of the linked image in placedLayer');
|
|
1946
|
-
|
|
1947
|
-
|
|
1948
|
-
|
|
1949
|
-
|
|
1925
|
+
const w = placed.width;
|
|
1926
|
+
const h = placed.height;
|
|
1927
|
+
const x0 = 0, x1 = w / 3, x2 = w * 2 / 3, x3 = w;
|
|
1928
|
+
const y0 = 0, y1 = h / 3, y2 = h * 2 / 3, y3 = h;
|
|
1950
1929
|
return {
|
|
1951
1930
|
style: 'custom',
|
|
1952
1931
|
value: 0,
|
|
@@ -1971,13 +1950,13 @@ function getWarpFromPlacedLayer(placed) {
|
|
|
1971
1950
|
},
|
|
1972
1951
|
};
|
|
1973
1952
|
}
|
|
1974
|
-
addHandler('SoLd', hasKey('placedLayer'),
|
|
1953
|
+
addHandler('SoLd', hasKey('placedLayer'), (reader, target, left) => {
|
|
1975
1954
|
if (readSignature(reader) !== 'soLD')
|
|
1976
|
-
throw new Error(
|
|
1977
|
-
|
|
1955
|
+
throw new Error(`Invalid SoLd type`);
|
|
1956
|
+
const version = readInt32(reader);
|
|
1978
1957
|
if (version !== 4 && version !== 5)
|
|
1979
|
-
throw new Error(
|
|
1980
|
-
|
|
1958
|
+
throw new Error(`Invalid SoLd version`);
|
|
1959
|
+
const desc = readVersionAndDescriptor(reader, true);
|
|
1981
1960
|
// console.log('SoLd', require('util').inspect(desc, false, 99, true));
|
|
1982
1961
|
// console.log('SoLd.warp', require('util').inspect(desc.warp, false, 99, true));
|
|
1983
1962
|
// console.log('SoLd.quiltWarp', require('util').inspect(desc.quiltWarp, false, 99, true));
|
|
@@ -2000,7 +1979,7 @@ addHandler('SoLd', hasKey('placedLayer'), function (reader, target, left) {
|
|
|
2000
1979
|
resolution: parseUnits(desc.Rslt),
|
|
2001
1980
|
warp: parseWarp((desc.quiltWarp || desc.warp)),
|
|
2002
1981
|
};
|
|
2003
|
-
if (desc.nonAffineTransform && desc.nonAffineTransform.some(
|
|
1982
|
+
if (desc.nonAffineTransform && desc.nonAffineTransform.some((x, i) => x !== desc.Trnf[i])) {
|
|
2004
1983
|
target.placedLayer.nonAffineTransform = desc.nonAffineTransform;
|
|
2005
1984
|
}
|
|
2006
1985
|
if (desc.Crop)
|
|
@@ -2017,15 +1996,15 @@ addHandler('SoLd', hasKey('placedLayer'), function (reader, target, left) {
|
|
|
2017
1996
|
target.placedLayer.filter = parseFilterFX(desc.filterFX, reader);
|
|
2018
1997
|
// console.log('filter', require('util').inspect(target.placedLayer.filter, false, 99, true));
|
|
2019
1998
|
skipBytes(reader, left()); // HACK
|
|
2020
|
-
},
|
|
1999
|
+
}, (writer, target) => {
|
|
2021
2000
|
var _a, _b;
|
|
2022
2001
|
writeSignature(writer, 'soLD');
|
|
2023
2002
|
writeInt32(writer, 4); // version
|
|
2024
|
-
|
|
2003
|
+
const placed = target.placedLayer;
|
|
2025
2004
|
if (!placed.id || typeof placed.id !== 'string' || !/^[0-9a-f]{8}-([0-9a-f]{4}-){3}[0-9a-f]{12}$/.test(placed.id)) {
|
|
2026
2005
|
throw new Error('Placed layer ID must be in a GUID format (example: 20953ddb-9391-11ec-b4f1-c15674f50bc4)');
|
|
2027
2006
|
}
|
|
2028
|
-
|
|
2007
|
+
const desc = Object.assign(Object.assign({ Idnt: placed.id, placed: (_a = placed.placed) !== null && _a !== void 0 ? _a : placed.id, PgNm: placed.pageNumber || 1, totalPages: placed.totalPages || 1 }, (placed.crop ? { Crop: placed.crop } : {})), { frameStep: placed.frameStep || { numerator: 0, denominator: 600 }, duration: placed.duration || { numerator: 0, denominator: 600 }, frameCount: placed.frameCount || 0, Annt: 16, Type: placedLayerTypes.indexOf(placed.type), Trnf: placed.transform, nonAffineTransform: (_b = placed.nonAffineTransform) !== null && _b !== void 0 ? _b : placed.transform,
|
|
2029
2008
|
// quiltWarp: {} as any,
|
|
2030
2009
|
warp: encodeWarp(getWarpFromPlacedLayer(placed)), 'Sz ': {
|
|
2031
2010
|
_name: '',
|
|
@@ -2042,7 +2021,7 @@ addHandler('SoLd', hasKey('placedLayer'), function (reader, target, left) {
|
|
|
2042
2021
|
filterMaskEnable: placed.filter.maskEnabled,
|
|
2043
2022
|
filterMaskLinked: placed.filter.maskLinked,
|
|
2044
2023
|
filterMaskExtendWithWhite: placed.filter.maskExtendWithWhite,
|
|
2045
|
-
filterFXList: placed.filter.list.map(
|
|
2024
|
+
filterFXList: placed.filter.list.map(f => serializeFilterFXItem(f)),
|
|
2046
2025
|
};
|
|
2047
2026
|
}
|
|
2048
2027
|
// TODO:
|
|
@@ -2060,7 +2039,7 @@ addHandler('SoLd', hasKey('placedLayer'), function (reader, target, left) {
|
|
|
2060
2039
|
// // throw new Error('DIFFERENT');
|
|
2061
2040
|
// }
|
|
2062
2041
|
if (placed.warp && isQuiltWarp(placed.warp)) {
|
|
2063
|
-
|
|
2042
|
+
const quiltWarp = encodeWarp(placed.warp);
|
|
2064
2043
|
desc.quiltWarp = quiltWarp;
|
|
2065
2044
|
desc.warp = {
|
|
2066
2045
|
warpStyle: 'warpStyle.warpNone',
|
|
@@ -2083,61 +2062,64 @@ addHandler('SoLd', hasKey('placedLayer'), function (reader, target, left) {
|
|
|
2083
2062
|
writeVersionAndDescriptor(writer, '', 'null', desc, desc.quiltWarp ? 'quiltWarp' : 'warp');
|
|
2084
2063
|
});
|
|
2085
2064
|
addHandlerAlias('SoLE', 'SoLd');
|
|
2086
|
-
addHandler('fxrp', hasKey('referencePoint'),
|
|
2065
|
+
addHandler('fxrp', hasKey('referencePoint'), (reader, target) => {
|
|
2087
2066
|
target.referencePoint = {
|
|
2088
2067
|
x: readFloat64(reader),
|
|
2089
2068
|
y: readFloat64(reader),
|
|
2090
2069
|
};
|
|
2091
|
-
},
|
|
2070
|
+
}, (writer, target) => {
|
|
2092
2071
|
writeFloat64(writer, target.referencePoint.x);
|
|
2093
2072
|
writeFloat64(writer, target.referencePoint.y);
|
|
2094
2073
|
});
|
|
2095
|
-
addHandler('Lr16',
|
|
2074
|
+
addHandler('Lr16', () => false, (reader, _target, _left, psd, imageResources) => {
|
|
2096
2075
|
readLayerInfo(reader, psd, imageResources);
|
|
2097
|
-
},
|
|
2076
|
+
}, (_writer, _target) => {
|
|
2098
2077
|
});
|
|
2099
|
-
addHandler('Lr32',
|
|
2078
|
+
addHandler('Lr32', () => false, (reader, _target, _left, psd, imageResources) => {
|
|
2100
2079
|
readLayerInfo(reader, psd, imageResources);
|
|
2101
|
-
},
|
|
2080
|
+
}, (_writer, _target) => {
|
|
2102
2081
|
});
|
|
2103
|
-
addHandler('LMsk', hasKey('userMask'),
|
|
2082
|
+
addHandler('LMsk', hasKey('userMask'), (reader, target) => {
|
|
2104
2083
|
target.userMask = {
|
|
2105
2084
|
colorSpace: readColor(reader),
|
|
2106
2085
|
opacity: readUint16(reader) / 0xff,
|
|
2107
2086
|
};
|
|
2108
|
-
|
|
2087
|
+
const flag = readUint8(reader);
|
|
2109
2088
|
if (flag !== 128)
|
|
2110
2089
|
throw new Error('Invalid flag value');
|
|
2111
2090
|
skipBytes(reader, 1);
|
|
2112
|
-
},
|
|
2113
|
-
|
|
2091
|
+
}, (writer, target) => {
|
|
2092
|
+
const userMask = target.userMask;
|
|
2114
2093
|
writeColor(writer, userMask.colorSpace);
|
|
2115
2094
|
writeUint16(writer, clamp(userMask.opacity, 0, 1) * 0xff);
|
|
2116
2095
|
writeUint8(writer, 128);
|
|
2117
2096
|
writeZeros(writer, 1);
|
|
2118
2097
|
});
|
|
2119
2098
|
if (MOCK_HANDLERS) {
|
|
2120
|
-
addHandler('Patt',
|
|
2099
|
+
addHandler('Patt', target => target._Patt !== undefined, (reader, target, left) => {
|
|
2121
2100
|
// console.log('additional info: Patt');
|
|
2122
2101
|
target._Patt = readBytes(reader, left());
|
|
2123
|
-
},
|
|
2102
|
+
}, (writer, target) => false && writeBytes(writer, target._Patt));
|
|
2124
2103
|
}
|
|
2125
2104
|
else {
|
|
2126
2105
|
addHandler('Patt', // TODO: handle also Pat2 & Pat3
|
|
2127
|
-
|
|
2128
|
-
target
|
|
2129
|
-
|
|
2130
|
-
|
|
2131
|
-
|
|
2132
|
-
|
|
2133
|
-
|
|
2134
|
-
|
|
2135
|
-
|
|
2136
|
-
|
|
2137
|
-
|
|
2138
|
-
|
|
2106
|
+
// TODO: handle also Pat2 & Pat3
|
|
2107
|
+
target => !!(target.patterns && target.patterns.length > 0), (reader, target, left) => {
|
|
2108
|
+
while (left() > 0) {
|
|
2109
|
+
const pattern = readPattern(reader);
|
|
2110
|
+
if (target.patterns === undefined)
|
|
2111
|
+
target.patterns = [];
|
|
2112
|
+
target.patterns.push(pattern);
|
|
2113
|
+
}
|
|
2114
|
+
}, (writer, target, _, _options) => {
|
|
2115
|
+
const patterns = target.patterns || [];
|
|
2116
|
+
for (const pattern of patterns) {
|
|
2117
|
+
writePattern(writer, pattern);
|
|
2118
|
+
}
|
|
2139
2119
|
});
|
|
2140
2120
|
}
|
|
2121
|
+
addHandlerAlias('Pat2', 'Patt');
|
|
2122
|
+
addHandlerAlias('Pat3', 'Patt');
|
|
2141
2123
|
/*
|
|
2142
2124
|
interface CAIDesc {
|
|
2143
2125
|
_name: '';
|
|
@@ -2161,9 +2143,9 @@ addHandler(
|
|
|
2161
2143
|
);
|
|
2162
2144
|
// */
|
|
2163
2145
|
if (MOCK_HANDLERS) {
|
|
2164
|
-
addHandler('CAI ',
|
|
2146
|
+
addHandler('CAI ', target => target._CAI_ !== undefined, (reader, target, left) => {
|
|
2165
2147
|
target._CAI_ = readBytes(reader, left());
|
|
2166
|
-
},
|
|
2148
|
+
}, (writer, target) => {
|
|
2167
2149
|
writeBytes(writer, target._CAI_);
|
|
2168
2150
|
});
|
|
2169
2151
|
}
|
|
@@ -2180,12 +2162,12 @@ if (MOCK_HANDLERS) {
|
|
|
2180
2162
|
// }
|
|
2181
2163
|
if (MOCK_HANDLERS) {
|
|
2182
2164
|
addHandler('OCIO', // document color management info
|
|
2183
|
-
|
|
2184
|
-
target
|
|
2165
|
+
// document color management info
|
|
2166
|
+
target => target._OCIO !== undefined, (reader, target, left) => {
|
|
2185
2167
|
// const desc = readVersionAndDescriptor(reader, true) as OCIODescriptor;
|
|
2186
2168
|
// console.log('OCIO', require('util').inspect(desc, false, 99, true));
|
|
2187
2169
|
target._OCIO = readBytes(reader, left());
|
|
2188
|
-
},
|
|
2170
|
+
}, (writer, target) => {
|
|
2189
2171
|
writeBytes(writer, target._OCIO);
|
|
2190
2172
|
});
|
|
2191
2173
|
}
|
|
@@ -2197,21 +2179,21 @@ if (MOCK_HANDLERS) {
|
|
|
2197
2179
|
// }
|
|
2198
2180
|
if (MOCK_HANDLERS) {
|
|
2199
2181
|
addHandler('GenI', // generative tech
|
|
2200
|
-
|
|
2201
|
-
target
|
|
2202
|
-
|
|
2182
|
+
// generative tech
|
|
2183
|
+
target => target._GenI !== undefined, (reader, target, left) => {
|
|
2184
|
+
const desc = readVersionAndDescriptor(reader, true); // as GenIDescriptor;
|
|
2203
2185
|
console.log('GenI', require('util').inspect(desc, false, 99, true));
|
|
2204
2186
|
target._GenI = readBytes(reader, left());
|
|
2205
|
-
},
|
|
2187
|
+
}, (writer, target) => {
|
|
2206
2188
|
writeBytes(writer, target._GenI);
|
|
2207
2189
|
});
|
|
2208
2190
|
}
|
|
2209
2191
|
function readRect(reader) {
|
|
2210
|
-
|
|
2211
|
-
|
|
2212
|
-
|
|
2213
|
-
|
|
2214
|
-
return { top
|
|
2192
|
+
const top = readInt32(reader);
|
|
2193
|
+
const left = readInt32(reader);
|
|
2194
|
+
const bottom = readInt32(reader);
|
|
2195
|
+
const right = readInt32(reader);
|
|
2196
|
+
return { top, left, bottom, right };
|
|
2215
2197
|
}
|
|
2216
2198
|
function writeRect(writer, rect) {
|
|
2217
2199
|
writeInt32(writer, rect.top);
|
|
@@ -2219,29 +2201,29 @@ function writeRect(writer, rect) {
|
|
|
2219
2201
|
writeInt32(writer, rect.bottom);
|
|
2220
2202
|
writeInt32(writer, rect.right);
|
|
2221
2203
|
}
|
|
2222
|
-
addHandler('Anno',
|
|
2223
|
-
|
|
2224
|
-
|
|
2204
|
+
addHandler('Anno', target => target.annotations !== undefined, (reader, target, left) => {
|
|
2205
|
+
const major = readUint16(reader);
|
|
2206
|
+
const minor = readUint16(reader);
|
|
2225
2207
|
if (major !== 2 || minor !== 1)
|
|
2226
2208
|
throw new Error('Invalid Anno version');
|
|
2227
|
-
|
|
2228
|
-
|
|
2229
|
-
for (
|
|
2209
|
+
const count = readUint32(reader);
|
|
2210
|
+
const annotations = [];
|
|
2211
|
+
for (let i = 0; i < count; i++) {
|
|
2230
2212
|
/*const length =*/ readUint32(reader);
|
|
2231
|
-
|
|
2232
|
-
|
|
2213
|
+
const type = readSignature(reader);
|
|
2214
|
+
const open = !!readUint8(reader);
|
|
2233
2215
|
/*const flags =*/ readUint8(reader); // always 28
|
|
2234
2216
|
/*const optionalBlocks =*/ readUint16(reader);
|
|
2235
|
-
|
|
2236
|
-
|
|
2237
|
-
|
|
2238
|
-
|
|
2239
|
-
|
|
2240
|
-
|
|
2217
|
+
const iconLocation = readRect(reader);
|
|
2218
|
+
const popupLocation = readRect(reader);
|
|
2219
|
+
const color = readColor(reader);
|
|
2220
|
+
const author = readPascalString(reader, 2);
|
|
2221
|
+
const name = readPascalString(reader, 2);
|
|
2222
|
+
const date = readPascalString(reader, 2);
|
|
2241
2223
|
/*const contentLength =*/ readUint32(reader);
|
|
2242
2224
|
/*const dataType =*/ readSignature(reader);
|
|
2243
|
-
|
|
2244
|
-
|
|
2225
|
+
const dataLength = readUint32(reader);
|
|
2226
|
+
let data;
|
|
2245
2227
|
if (type === 'txtA') {
|
|
2246
2228
|
if (dataLength >= 2 && readUint16(reader) === 0xfeff) {
|
|
2247
2229
|
data = readUnicodeStringWithLength(reader, (dataLength - 2) / 2);
|
|
@@ -2259,32 +2241,23 @@ addHandler('Anno', function (target) { return target.annotations !== undefined;
|
|
|
2259
2241
|
throw new Error('Unknown annotation type');
|
|
2260
2242
|
}
|
|
2261
2243
|
annotations.push({
|
|
2262
|
-
type: type === 'txtA' ? 'text' : 'sound',
|
|
2263
|
-
open: open_1,
|
|
2264
|
-
iconLocation: iconLocation,
|
|
2265
|
-
popupLocation: popupLocation,
|
|
2266
|
-
color: color,
|
|
2267
|
-
author: author,
|
|
2268
|
-
name: name_2,
|
|
2269
|
-
date: date,
|
|
2270
|
-
data: data,
|
|
2244
|
+
type: type === 'txtA' ? 'text' : 'sound', open, iconLocation, popupLocation, color, author, name, date, data,
|
|
2271
2245
|
});
|
|
2272
2246
|
}
|
|
2273
2247
|
target.annotations = annotations;
|
|
2274
2248
|
skipBytes(reader, left());
|
|
2275
|
-
},
|
|
2276
|
-
|
|
2249
|
+
}, (writer, target) => {
|
|
2250
|
+
const annotations = target.annotations;
|
|
2277
2251
|
writeUint16(writer, 2);
|
|
2278
2252
|
writeUint16(writer, 1);
|
|
2279
2253
|
writeUint32(writer, annotations.length);
|
|
2280
|
-
for (
|
|
2281
|
-
|
|
2282
|
-
var sound = annotation.type === 'sound';
|
|
2254
|
+
for (const annotation of annotations) {
|
|
2255
|
+
const sound = annotation.type === 'sound';
|
|
2283
2256
|
if (sound && !(annotation.data instanceof Uint8Array))
|
|
2284
2257
|
throw new Error('Sound annotation data should be Uint8Array');
|
|
2285
2258
|
if (!sound && typeof annotation.data !== 'string')
|
|
2286
2259
|
throw new Error('Text annotation data should be string');
|
|
2287
|
-
|
|
2260
|
+
const lengthOffset = writer.offset;
|
|
2288
2261
|
writeUint32(writer, 0); // length
|
|
2289
2262
|
writeSignature(writer, sound ? 'sndA' : 'txtA');
|
|
2290
2263
|
writeUint8(writer, annotation.open ? 1 : 0);
|
|
@@ -2296,18 +2269,18 @@ addHandler('Anno', function (target) { return target.annotations !== undefined;
|
|
|
2296
2269
|
writePascalString(writer, annotation.author || '', 2);
|
|
2297
2270
|
writePascalString(writer, annotation.name || '', 2);
|
|
2298
2271
|
writePascalString(writer, annotation.date || '', 2);
|
|
2299
|
-
|
|
2272
|
+
const contentOffset = writer.offset;
|
|
2300
2273
|
writeUint32(writer, 0); // content length
|
|
2301
2274
|
writeSignature(writer, sound ? 'sndM' : 'txtC');
|
|
2302
2275
|
writeUint32(writer, 0); // data length
|
|
2303
|
-
|
|
2276
|
+
const dataOffset = writer.offset;
|
|
2304
2277
|
if (sound) {
|
|
2305
2278
|
writeBytes(writer, annotation.data);
|
|
2306
2279
|
}
|
|
2307
2280
|
else {
|
|
2308
2281
|
writeUint16(writer, 0xfeff); // unicode string indicator
|
|
2309
|
-
|
|
2310
|
-
for (
|
|
2282
|
+
const text = annotation.data.replace(/\n/g, '\r');
|
|
2283
|
+
for (let i = 0; i < text.length; i++)
|
|
2311
2284
|
writeUint16(writer, text.charCodeAt(i));
|
|
2312
2285
|
}
|
|
2313
2286
|
writer.view.setUint32(lengthOffset, writer.offset - lengthOffset, false);
|
|
@@ -2316,33 +2289,33 @@ addHandler('Anno', function (target) { return target.annotations !== undefined;
|
|
|
2316
2289
|
}
|
|
2317
2290
|
});
|
|
2318
2291
|
function createLnkHandler(tag) {
|
|
2319
|
-
addHandler(tag,
|
|
2320
|
-
|
|
2292
|
+
addHandler(tag, (target) => {
|
|
2293
|
+
const psd = target;
|
|
2321
2294
|
if (!psd.linkedFiles || !psd.linkedFiles.length)
|
|
2322
2295
|
return false;
|
|
2323
|
-
if (tag === 'lnkE' && !psd.linkedFiles.some(
|
|
2296
|
+
if (tag === 'lnkE' && !psd.linkedFiles.some(f => f.linkedFile))
|
|
2324
2297
|
return false;
|
|
2325
2298
|
return true;
|
|
2326
|
-
},
|
|
2327
|
-
|
|
2299
|
+
}, (reader, target, left, _psd) => {
|
|
2300
|
+
const psd = target;
|
|
2328
2301
|
psd.linkedFiles = psd.linkedFiles || [];
|
|
2329
2302
|
while (left() > 8) {
|
|
2330
|
-
|
|
2331
|
-
|
|
2332
|
-
|
|
2303
|
+
let size = readLength64(reader);
|
|
2304
|
+
const startOffset = reader.offset;
|
|
2305
|
+
const type = readSignature(reader);
|
|
2333
2306
|
// liFD - linked file data
|
|
2334
2307
|
// liFE - linked file external
|
|
2335
2308
|
// liFA - linked file alias
|
|
2336
|
-
|
|
2337
|
-
|
|
2338
|
-
|
|
2339
|
-
|
|
2340
|
-
|
|
2341
|
-
|
|
2342
|
-
|
|
2343
|
-
|
|
2344
|
-
|
|
2345
|
-
|
|
2309
|
+
const version = readInt32(reader);
|
|
2310
|
+
const id = readPascalString(reader, 1);
|
|
2311
|
+
const name = readUnicodeString(reader);
|
|
2312
|
+
const fileType = readSignature(reader).trim(); // ' ' if empty
|
|
2313
|
+
const fileCreator = readSignature(reader).trim(); // ' ' or '\0\0\0\0' if empty
|
|
2314
|
+
const dataSize = readLength64(reader);
|
|
2315
|
+
const hasFileOpenDescriptor = readUint8(reader);
|
|
2316
|
+
const fileOpenDescriptor = hasFileOpenDescriptor ? readVersionAndDescriptor(reader) : undefined;
|
|
2317
|
+
const linkedFileDescriptor = type === 'liFE' ? readVersionAndDescriptor(reader) : undefined;
|
|
2318
|
+
const file = { id, name };
|
|
2346
2319
|
if (fileType)
|
|
2347
2320
|
file.type = fileType;
|
|
2348
2321
|
if (fileCreator)
|
|
@@ -2356,17 +2329,17 @@ function createLnkHandler(tag) {
|
|
|
2356
2329
|
};
|
|
2357
2330
|
}
|
|
2358
2331
|
if (type === 'liFE' && version > 3) {
|
|
2359
|
-
|
|
2360
|
-
|
|
2361
|
-
|
|
2362
|
-
|
|
2363
|
-
|
|
2364
|
-
|
|
2365
|
-
|
|
2366
|
-
|
|
2332
|
+
const year = readInt32(reader);
|
|
2333
|
+
const month = readUint8(reader);
|
|
2334
|
+
const day = readUint8(reader);
|
|
2335
|
+
const hour = readUint8(reader);
|
|
2336
|
+
const minute = readUint8(reader);
|
|
2337
|
+
const seconds = readFloat64(reader);
|
|
2338
|
+
const wholeSeconds = Math.floor(seconds);
|
|
2339
|
+
const ms = (seconds - wholeSeconds) * 1000;
|
|
2367
2340
|
file.time = (new Date(Date.UTC(year, month, day, hour, minute, wholeSeconds, ms))).toISOString();
|
|
2368
2341
|
}
|
|
2369
|
-
|
|
2342
|
+
const fileSize = type === 'liFE' ? readLength64(reader) : 0;
|
|
2370
2343
|
if (type === 'liFA')
|
|
2371
2344
|
skipBytes(reader, 8);
|
|
2372
2345
|
if (type === 'liFD')
|
|
@@ -2383,7 +2356,7 @@ function createLnkHandler(tag) {
|
|
|
2383
2356
|
file.data = undefined;
|
|
2384
2357
|
if (tag === 'lnkE') {
|
|
2385
2358
|
file.linkedFile = {
|
|
2386
|
-
fileSize
|
|
2359
|
+
fileSize,
|
|
2387
2360
|
name: (linkedFileDescriptor === null || linkedFileDescriptor === void 0 ? void 0 : linkedFileDescriptor['Nm ']) || '',
|
|
2388
2361
|
fullPath: (linkedFileDescriptor === null || linkedFileDescriptor === void 0 ? void 0 : linkedFileDescriptor.fullPath) || '',
|
|
2389
2362
|
originalPath: (linkedFileDescriptor === null || linkedFileDescriptor === void 0 ? void 0 : linkedFileDescriptor.originalPath) || '',
|
|
@@ -2396,14 +2369,13 @@ function createLnkHandler(tag) {
|
|
|
2396
2369
|
reader.offset = startOffset + size;
|
|
2397
2370
|
}
|
|
2398
2371
|
skipBytes(reader, left()); // ?
|
|
2399
|
-
},
|
|
2372
|
+
}, (writer, target) => {
|
|
2400
2373
|
var _a, _b, _c, _d, _e, _f, _g, _h, _j;
|
|
2401
|
-
|
|
2402
|
-
for (
|
|
2403
|
-
var file = _k[_i];
|
|
2374
|
+
const psd = target;
|
|
2375
|
+
for (const file of psd.linkedFiles) {
|
|
2404
2376
|
if ((tag === 'lnkE') !== !!file.linkedFile)
|
|
2405
2377
|
continue;
|
|
2406
|
-
|
|
2378
|
+
let version = 2;
|
|
2407
2379
|
if (file.assetLockedState != null)
|
|
2408
2380
|
version = 7;
|
|
2409
2381
|
else if (file.assetModTime != null)
|
|
@@ -2413,7 +2385,7 @@ function createLnkHandler(tag) {
|
|
|
2413
2385
|
else if (tag === 'lnkE')
|
|
2414
2386
|
version = 3;
|
|
2415
2387
|
writeLength64(writer, 0);
|
|
2416
|
-
|
|
2388
|
+
const sizeOffset = writer.offset;
|
|
2417
2389
|
writeSignature(writer, (tag === 'lnkE') ? 'liFE' : (file.data ? 'liFD' : 'liFA'));
|
|
2418
2390
|
writeInt32(writer, version);
|
|
2419
2391
|
if (!file.id || typeof file.id !== 'string' || !/^[0-9a-f]{8}-([0-9a-f]{4}-){3}[0-9a-f]{12}$/.test(file.id)) {
|
|
@@ -2421,11 +2393,11 @@ function createLnkHandler(tag) {
|
|
|
2421
2393
|
}
|
|
2422
2394
|
writePascalString(writer, file.id, 1);
|
|
2423
2395
|
writeUnicodeStringWithPadding(writer, file.name || '');
|
|
2424
|
-
writeSignature(writer, file.type ?
|
|
2425
|
-
writeSignature(writer, file.creator ?
|
|
2396
|
+
writeSignature(writer, file.type ? `${file.type} `.substring(0, 4) : ' ');
|
|
2397
|
+
writeSignature(writer, file.creator ? `${file.creator} `.substring(0, 4) : '\0\0\0\0');
|
|
2426
2398
|
writeLength64(writer, file.data ? file.data.byteLength : 0);
|
|
2427
2399
|
if (file.descriptor && file.descriptor.compInfo) {
|
|
2428
|
-
|
|
2400
|
+
const desc = {
|
|
2429
2401
|
compInfo: {
|
|
2430
2402
|
compID: file.descriptor.compInfo.compID,
|
|
2431
2403
|
originalCompID: file.descriptor.compInfo.originalCompID,
|
|
@@ -2438,7 +2410,7 @@ function createLnkHandler(tag) {
|
|
|
2438
2410
|
writeUint8(writer, 0);
|
|
2439
2411
|
}
|
|
2440
2412
|
if (tag === 'lnkE') {
|
|
2441
|
-
|
|
2413
|
+
const desc = {
|
|
2442
2414
|
descVersion: 2,
|
|
2443
2415
|
'Nm ': (_b = (_a = file.linkedFile) === null || _a === void 0 ? void 0 : _a.name) !== null && _b !== void 0 ? _b : '',
|
|
2444
2416
|
fullPath: (_d = (_c = file.linkedFile) === null || _c === void 0 ? void 0 : _c.fullPath) !== null && _d !== void 0 ? _d : '',
|
|
@@ -2446,7 +2418,7 @@ function createLnkHandler(tag) {
|
|
|
2446
2418
|
relPath: (_h = (_g = file.linkedFile) === null || _g === void 0 ? void 0 : _g.relativePath) !== null && _h !== void 0 ? _h : '',
|
|
2447
2419
|
};
|
|
2448
2420
|
writeVersionAndDescriptor(writer, '', 'ExternalFileLink', desc);
|
|
2449
|
-
|
|
2421
|
+
const time = file.time ? new Date(file.time) : new Date();
|
|
2450
2422
|
writeInt32(writer, time.getUTCFullYear());
|
|
2451
2423
|
writeUint8(writer, time.getUTCMonth());
|
|
2452
2424
|
writeUint8(writer, time.getUTCDate());
|
|
@@ -2466,7 +2438,7 @@ function createLnkHandler(tag) {
|
|
|
2466
2438
|
writeFloat64(writer, file.assetModTime || 0);
|
|
2467
2439
|
if (version >= 7)
|
|
2468
2440
|
writeUint8(writer, file.assetLockedState || 0);
|
|
2469
|
-
|
|
2441
|
+
let size = writer.offset - sizeOffset;
|
|
2470
2442
|
writer.view.setUint32(sizeOffset - 4, size, false); // write size
|
|
2471
2443
|
while (size % 4) {
|
|
2472
2444
|
size++;
|
|
@@ -2479,20 +2451,20 @@ createLnkHandler('lnk2');
|
|
|
2479
2451
|
createLnkHandler('lnkE');
|
|
2480
2452
|
addHandlerAlias('lnkD', 'lnk2');
|
|
2481
2453
|
addHandlerAlias('lnk3', 'lnk2');
|
|
2482
|
-
addHandler('pths', hasKey('pathList'),
|
|
2483
|
-
|
|
2454
|
+
addHandler('pths', hasKey('pathList'), (reader, target) => {
|
|
2455
|
+
const desc = readVersionAndDescriptor(reader, true);
|
|
2484
2456
|
// console.log(require('util').inspect(desc, false, 99, true));
|
|
2485
2457
|
// if (options.throwForMissingFeatures && desc?.pathList?.length) throw new Error('non-empty pathList in `pths`');
|
|
2486
2458
|
desc;
|
|
2487
2459
|
target.pathList = []; // TODO: read paths
|
|
2488
|
-
},
|
|
2489
|
-
|
|
2460
|
+
}, (writer, _target) => {
|
|
2461
|
+
const desc = {
|
|
2490
2462
|
pathList: [], // TODO: write paths
|
|
2491
2463
|
};
|
|
2492
2464
|
writeVersionAndDescriptor(writer, '', 'pathsDataClass', desc);
|
|
2493
2465
|
});
|
|
2494
|
-
addHandler('lyvr', hasKey('version'),
|
|
2495
|
-
addHandler('lfxs',
|
|
2466
|
+
addHandler('lyvr', hasKey('version'), (reader, target) => target.version = readUint32(reader), (writer, target) => writeUint32(writer, target.version));
|
|
2467
|
+
addHandler('lfxs', () => false, // TODO: not sure when we actually need to write this section
|
|
2496
2468
|
// NOTE: this might be insufficient
|
|
2497
2469
|
// target => target.effects !== undefined && (
|
|
2498
2470
|
// !!target.effects.dropShadow?.some(e => e.choke) ||
|
|
@@ -2500,22 +2472,22 @@ addHandler('lfxs', function () { return false; }, // TODO: not sure when we actu
|
|
|
2500
2472
|
// !!target.effects.outerGlow?.choke ||
|
|
2501
2473
|
// !!target.effects.innerGlow?.choke
|
|
2502
2474
|
// ),
|
|
2503
|
-
|
|
2504
|
-
|
|
2475
|
+
(reader, target, left) => {
|
|
2476
|
+
const version = readUint32(reader);
|
|
2505
2477
|
if (version !== 0)
|
|
2506
|
-
throw new Error(
|
|
2507
|
-
|
|
2478
|
+
throw new Error(`Invalid lfxs version`);
|
|
2479
|
+
const desc = readVersionAndDescriptor(reader);
|
|
2508
2480
|
target.effects = parseEffects(desc, !!reader.logMissingFeatures);
|
|
2509
2481
|
skipBytes(reader, left());
|
|
2510
|
-
},
|
|
2511
|
-
|
|
2482
|
+
}, (writer, target, _, options) => {
|
|
2483
|
+
const desc = serializeEffects(target.effects, !!options.logMissingFeatures, true);
|
|
2512
2484
|
writeUint32(writer, 0); // version
|
|
2513
2485
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
2514
2486
|
});
|
|
2515
2487
|
function adjustmentType(type) {
|
|
2516
|
-
return
|
|
2488
|
+
return (target) => !!target.adjustment && target.adjustment.type === type;
|
|
2517
2489
|
}
|
|
2518
|
-
addHandler('brit', adjustmentType('brightness/contrast'),
|
|
2490
|
+
addHandler('brit', adjustmentType('brightness/contrast'), (reader, target, left) => {
|
|
2519
2491
|
if (!target.adjustment) { // ignore if got one from CgEd block
|
|
2520
2492
|
target.adjustment = {
|
|
2521
2493
|
type: 'brightness/contrast',
|
|
@@ -2527,9 +2499,9 @@ addHandler('brit', adjustmentType('brightness/contrast'), function (reader, targ
|
|
|
2527
2499
|
};
|
|
2528
2500
|
}
|
|
2529
2501
|
skipBytes(reader, left());
|
|
2530
|
-
},
|
|
2502
|
+
}, (writer, target) => {
|
|
2531
2503
|
var _a;
|
|
2532
|
-
|
|
2504
|
+
const info = target.adjustment;
|
|
2533
2505
|
writeInt16(writer, info.brightness || 0);
|
|
2534
2506
|
writeInt16(writer, info.contrast || 0);
|
|
2535
2507
|
writeInt16(writer, (_a = info.meanValue) !== null && _a !== void 0 ? _a : 127);
|
|
@@ -2537,12 +2509,12 @@ addHandler('brit', adjustmentType('brightness/contrast'), function (reader, targ
|
|
|
2537
2509
|
writeZeros(writer, 1);
|
|
2538
2510
|
});
|
|
2539
2511
|
function readLevelsChannel(reader) {
|
|
2540
|
-
|
|
2541
|
-
|
|
2542
|
-
|
|
2543
|
-
|
|
2544
|
-
|
|
2545
|
-
return { shadowInput
|
|
2512
|
+
const shadowInput = readInt16(reader);
|
|
2513
|
+
const highlightInput = readInt16(reader);
|
|
2514
|
+
const shadowOutput = readInt16(reader);
|
|
2515
|
+
const highlightOutput = readInt16(reader);
|
|
2516
|
+
const midtoneInput = readInt16(reader) / 100;
|
|
2517
|
+
return { shadowInput, highlightInput, shadowOutput, highlightOutput, midtoneInput };
|
|
2546
2518
|
}
|
|
2547
2519
|
function writeLevelsChannel(writer, channel) {
|
|
2548
2520
|
writeInt16(writer, channel.shadowInput);
|
|
@@ -2551,14 +2523,14 @@ function writeLevelsChannel(writer, channel) {
|
|
|
2551
2523
|
writeInt16(writer, channel.highlightOutput);
|
|
2552
2524
|
writeInt16(writer, Math.round(channel.midtoneInput * 100));
|
|
2553
2525
|
}
|
|
2554
|
-
addHandler('levl', adjustmentType('levels'),
|
|
2526
|
+
addHandler('levl', adjustmentType('levels'), (reader, target, left) => {
|
|
2555
2527
|
if (readUint16(reader) !== 2)
|
|
2556
2528
|
throw new Error('Invalid levl version');
|
|
2557
|
-
target.adjustment =
|
|
2529
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), { type: 'levels', rgb: readLevelsChannel(reader), red: readLevelsChannel(reader), green: readLevelsChannel(reader), blue: readLevelsChannel(reader) });
|
|
2558
2530
|
skipBytes(reader, left());
|
|
2559
|
-
},
|
|
2560
|
-
|
|
2561
|
-
|
|
2531
|
+
}, (writer, target) => {
|
|
2532
|
+
const info = target.adjustment;
|
|
2533
|
+
const defaultChannel = {
|
|
2562
2534
|
shadowInput: 0,
|
|
2563
2535
|
highlightInput: 255,
|
|
2564
2536
|
shadowOutput: 0,
|
|
@@ -2570,34 +2542,33 @@ addHandler('levl', adjustmentType('levels'), function (reader, target, left) {
|
|
|
2570
2542
|
writeLevelsChannel(writer, info.red || defaultChannel);
|
|
2571
2543
|
writeLevelsChannel(writer, info.blue || defaultChannel);
|
|
2572
2544
|
writeLevelsChannel(writer, info.green || defaultChannel);
|
|
2573
|
-
for (
|
|
2545
|
+
for (let i = 0; i < 59; i++)
|
|
2574
2546
|
writeLevelsChannel(writer, defaultChannel);
|
|
2575
2547
|
});
|
|
2576
2548
|
function readCurveChannel(reader) {
|
|
2577
|
-
|
|
2578
|
-
|
|
2579
|
-
for (
|
|
2580
|
-
|
|
2581
|
-
|
|
2582
|
-
channel.push({ input
|
|
2549
|
+
const nodes = readUint16(reader);
|
|
2550
|
+
const channel = [];
|
|
2551
|
+
for (let j = 0; j < nodes; j++) {
|
|
2552
|
+
const output = readInt16(reader);
|
|
2553
|
+
const input = readInt16(reader);
|
|
2554
|
+
channel.push({ input, output });
|
|
2583
2555
|
}
|
|
2584
2556
|
return channel;
|
|
2585
2557
|
}
|
|
2586
2558
|
function writeCurveChannel(writer, channel) {
|
|
2587
2559
|
writeUint16(writer, channel.length);
|
|
2588
|
-
for (
|
|
2589
|
-
var n = channel_1[_i];
|
|
2560
|
+
for (const n of channel) {
|
|
2590
2561
|
writeUint16(writer, n.output);
|
|
2591
2562
|
writeUint16(writer, n.input);
|
|
2592
2563
|
}
|
|
2593
2564
|
}
|
|
2594
|
-
addHandler('curv', adjustmentType('curves'),
|
|
2565
|
+
addHandler('curv', adjustmentType('curves'), (reader, target, left) => {
|
|
2595
2566
|
readUint8(reader);
|
|
2596
2567
|
if (readUint16(reader) !== 1)
|
|
2597
2568
|
throw new Error('Invalid curv version');
|
|
2598
2569
|
readUint16(reader);
|
|
2599
|
-
|
|
2600
|
-
|
|
2570
|
+
const channels = readUint16(reader);
|
|
2571
|
+
const info = { type: 'curves' };
|
|
2601
2572
|
if (channels & 1)
|
|
2602
2573
|
info.rgb = readCurveChannel(reader);
|
|
2603
2574
|
if (channels & 2)
|
|
@@ -2606,7 +2577,7 @@ addHandler('curv', adjustmentType('curves'), function (reader, target, left) {
|
|
|
2606
2577
|
info.green = readCurveChannel(reader);
|
|
2607
2578
|
if (channels & 8)
|
|
2608
2579
|
info.blue = readCurveChannel(reader);
|
|
2609
|
-
target.adjustment =
|
|
2580
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), info);
|
|
2610
2581
|
// ignoring, duplicate information
|
|
2611
2582
|
// checkSignature(reader, 'Crv ');
|
|
2612
2583
|
// const cVersion = readUint16(reader);
|
|
@@ -2621,11 +2592,11 @@ addHandler('curv', adjustmentType('curves'), function (reader, target, left) {
|
|
|
2621
2592
|
// }
|
|
2622
2593
|
// }
|
|
2623
2594
|
skipBytes(reader, left());
|
|
2624
|
-
},
|
|
2625
|
-
|
|
2626
|
-
|
|
2627
|
-
|
|
2628
|
-
|
|
2595
|
+
}, (writer, target) => {
|
|
2596
|
+
const info = target.adjustment;
|
|
2597
|
+
const { rgb, red, green, blue } = info;
|
|
2598
|
+
let channels = 0;
|
|
2599
|
+
let channelCount = 0;
|
|
2629
2600
|
if (rgb && rgb.length) {
|
|
2630
2601
|
channels |= 1;
|
|
2631
2602
|
channelCount++;
|
|
@@ -2675,30 +2646,30 @@ addHandler('curv', adjustmentType('curves'), function (reader, target, left) {
|
|
|
2675
2646
|
writeCurveChannel(writer, blue);
|
|
2676
2647
|
}
|
|
2677
2648
|
});
|
|
2678
|
-
addHandler('expA', adjustmentType('exposure'),
|
|
2649
|
+
addHandler('expA', adjustmentType('exposure'), (reader, target, left) => {
|
|
2679
2650
|
if (readUint16(reader) !== 1)
|
|
2680
2651
|
throw new Error('Invalid expA version');
|
|
2681
|
-
target.adjustment =
|
|
2652
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), { type: 'exposure', exposure: readFloat32(reader), offset: readFloat32(reader), gamma: readFloat32(reader) });
|
|
2682
2653
|
skipBytes(reader, left());
|
|
2683
|
-
},
|
|
2684
|
-
|
|
2654
|
+
}, (writer, target) => {
|
|
2655
|
+
const info = target.adjustment;
|
|
2685
2656
|
writeUint16(writer, 1); // version
|
|
2686
2657
|
writeFloat32(writer, info.exposure);
|
|
2687
2658
|
writeFloat32(writer, info.offset);
|
|
2688
2659
|
writeFloat32(writer, info.gamma);
|
|
2689
2660
|
writeZeros(writer, 2);
|
|
2690
2661
|
});
|
|
2691
|
-
addHandler('vibA', adjustmentType('vibrance'),
|
|
2692
|
-
|
|
2662
|
+
addHandler('vibA', adjustmentType('vibrance'), (reader, target, left) => {
|
|
2663
|
+
const desc = readVersionAndDescriptor(reader);
|
|
2693
2664
|
target.adjustment = { type: 'vibrance' };
|
|
2694
2665
|
if (desc.vibrance !== undefined)
|
|
2695
2666
|
target.adjustment.vibrance = desc.vibrance;
|
|
2696
2667
|
if (desc.Strt !== undefined)
|
|
2697
2668
|
target.adjustment.saturation = desc.Strt;
|
|
2698
2669
|
skipBytes(reader, left());
|
|
2699
|
-
},
|
|
2700
|
-
|
|
2701
|
-
|
|
2670
|
+
}, (writer, target) => {
|
|
2671
|
+
const info = target.adjustment;
|
|
2672
|
+
const desc = {};
|
|
2702
2673
|
if (info.vibrance !== undefined)
|
|
2703
2674
|
desc.vibrance = info.vibrance;
|
|
2704
2675
|
if (info.saturation !== undefined)
|
|
@@ -2717,7 +2688,7 @@ function readHueChannel(reader) {
|
|
|
2717
2688
|
};
|
|
2718
2689
|
}
|
|
2719
2690
|
function writeHueChannel(writer, channel) {
|
|
2720
|
-
|
|
2691
|
+
const c = channel || {};
|
|
2721
2692
|
writeInt16(writer, c.a || 0);
|
|
2722
2693
|
writeInt16(writer, c.b || 0);
|
|
2723
2694
|
writeInt16(writer, c.c || 0);
|
|
@@ -2726,13 +2697,13 @@ function writeHueChannel(writer, channel) {
|
|
|
2726
2697
|
writeInt16(writer, c.saturation || 0);
|
|
2727
2698
|
writeInt16(writer, c.lightness || 0);
|
|
2728
2699
|
}
|
|
2729
|
-
addHandler('hue2', adjustmentType('hue/saturation'),
|
|
2700
|
+
addHandler('hue2', adjustmentType('hue/saturation'), (reader, target, left) => {
|
|
2730
2701
|
if (readUint16(reader) !== 2)
|
|
2731
2702
|
throw new Error('Invalid hue2 version');
|
|
2732
|
-
target.adjustment =
|
|
2703
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), { type: 'hue/saturation', master: readHueChannel(reader), reds: readHueChannel(reader), yellows: readHueChannel(reader), greens: readHueChannel(reader), cyans: readHueChannel(reader), blues: readHueChannel(reader), magentas: readHueChannel(reader) });
|
|
2733
2704
|
skipBytes(reader, left());
|
|
2734
|
-
},
|
|
2735
|
-
|
|
2705
|
+
}, (writer, target) => {
|
|
2706
|
+
const info = target.adjustment;
|
|
2736
2707
|
writeUint16(writer, 2); // version
|
|
2737
2708
|
writeHueChannel(writer, info.master);
|
|
2738
2709
|
writeHueChannel(writer, info.reds);
|
|
@@ -2754,7 +2725,7 @@ function writeColorBalance(writer, value) {
|
|
|
2754
2725
|
writeInt16(writer, value.magentaGreen || 0);
|
|
2755
2726
|
writeInt16(writer, value.yellowBlue || 0);
|
|
2756
2727
|
}
|
|
2757
|
-
addHandler('blnc', adjustmentType('color balance'),
|
|
2728
|
+
addHandler('blnc', adjustmentType('color balance'), (reader, target, left) => {
|
|
2758
2729
|
target.adjustment = {
|
|
2759
2730
|
type: 'color balance',
|
|
2760
2731
|
shadows: readColorBalance(reader),
|
|
@@ -2763,16 +2734,16 @@ addHandler('blnc', adjustmentType('color balance'), function (reader, target, le
|
|
|
2763
2734
|
preserveLuminosity: !!readUint8(reader),
|
|
2764
2735
|
};
|
|
2765
2736
|
skipBytes(reader, left());
|
|
2766
|
-
},
|
|
2767
|
-
|
|
2737
|
+
}, (writer, target) => {
|
|
2738
|
+
const info = target.adjustment;
|
|
2768
2739
|
writeColorBalance(writer, info.shadows || {});
|
|
2769
2740
|
writeColorBalance(writer, info.midtones || {});
|
|
2770
2741
|
writeColorBalance(writer, info.highlights || {});
|
|
2771
2742
|
writeUint8(writer, info.preserveLuminosity ? 1 : 0);
|
|
2772
2743
|
writeZeros(writer, 1);
|
|
2773
2744
|
});
|
|
2774
|
-
addHandler('blwh', adjustmentType('black & white'),
|
|
2775
|
-
|
|
2745
|
+
addHandler('blwh', adjustmentType('black & white'), (reader, target, left) => {
|
|
2746
|
+
const desc = readVersionAndDescriptor(reader);
|
|
2776
2747
|
target.adjustment = {
|
|
2777
2748
|
type: 'black & white',
|
|
2778
2749
|
reds: desc['Rd '],
|
|
@@ -2788,9 +2759,9 @@ addHandler('blwh', adjustmentType('black & white'), function (reader, target, le
|
|
|
2788
2759
|
if (desc.tintColor !== undefined)
|
|
2789
2760
|
target.adjustment.tintColor = parseColor(desc.tintColor);
|
|
2790
2761
|
skipBytes(reader, left());
|
|
2791
|
-
},
|
|
2792
|
-
|
|
2793
|
-
|
|
2762
|
+
}, (writer, target) => {
|
|
2763
|
+
const info = target.adjustment;
|
|
2764
|
+
const desc = {
|
|
2794
2765
|
'Rd ': info.reds || 0,
|
|
2795
2766
|
Yllw: info.yellows || 0,
|
|
2796
2767
|
'Grn ': info.greens || 0,
|
|
@@ -2804,11 +2775,11 @@ addHandler('blwh', adjustmentType('black & white'), function (reader, target, le
|
|
|
2804
2775
|
};
|
|
2805
2776
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
2806
2777
|
});
|
|
2807
|
-
addHandler('phfl', adjustmentType('photo filter'),
|
|
2808
|
-
|
|
2778
|
+
addHandler('phfl', adjustmentType('photo filter'), (reader, target, left) => {
|
|
2779
|
+
const version = readUint16(reader);
|
|
2809
2780
|
if (version !== 2 && version !== 3)
|
|
2810
2781
|
throw new Error('Invalid phfl version');
|
|
2811
|
-
|
|
2782
|
+
let color;
|
|
2812
2783
|
if (version === 2) {
|
|
2813
2784
|
color = readColor(reader);
|
|
2814
2785
|
}
|
|
@@ -2822,13 +2793,13 @@ addHandler('phfl', adjustmentType('photo filter'), function (reader, target, lef
|
|
|
2822
2793
|
}
|
|
2823
2794
|
target.adjustment = {
|
|
2824
2795
|
type: 'photo filter',
|
|
2825
|
-
color
|
|
2796
|
+
color,
|
|
2826
2797
|
density: readUint32(reader) / 100,
|
|
2827
2798
|
preserveLuminosity: !!readUint8(reader),
|
|
2828
2799
|
};
|
|
2829
2800
|
skipBytes(reader, left());
|
|
2830
|
-
},
|
|
2831
|
-
|
|
2801
|
+
}, (writer, target) => {
|
|
2802
|
+
const info = target.adjustment;
|
|
2832
2803
|
writeUint16(writer, 2); // version
|
|
2833
2804
|
writeColor(writer, info.color || { l: 0, a: 0, b: 0 });
|
|
2834
2805
|
writeUint32(writer, (info.density || 0) * 100);
|
|
@@ -2836,25 +2807,25 @@ addHandler('phfl', adjustmentType('photo filter'), function (reader, target, lef
|
|
|
2836
2807
|
writeZeros(writer, 3);
|
|
2837
2808
|
});
|
|
2838
2809
|
function readMixrChannel(reader) {
|
|
2839
|
-
|
|
2840
|
-
|
|
2841
|
-
|
|
2810
|
+
const red = readInt16(reader);
|
|
2811
|
+
const green = readInt16(reader);
|
|
2812
|
+
const blue = readInt16(reader);
|
|
2842
2813
|
skipBytes(reader, 2);
|
|
2843
|
-
|
|
2844
|
-
return { red
|
|
2814
|
+
const constant = readInt16(reader);
|
|
2815
|
+
return { red, green, blue, constant };
|
|
2845
2816
|
}
|
|
2846
2817
|
function writeMixrChannel(writer, channel) {
|
|
2847
|
-
|
|
2818
|
+
const c = channel || {};
|
|
2848
2819
|
writeInt16(writer, c.red);
|
|
2849
2820
|
writeInt16(writer, c.green);
|
|
2850
2821
|
writeInt16(writer, c.blue);
|
|
2851
2822
|
writeZeros(writer, 2);
|
|
2852
2823
|
writeInt16(writer, c.constant);
|
|
2853
2824
|
}
|
|
2854
|
-
addHandler('mixr', adjustmentType('channel mixer'),
|
|
2825
|
+
addHandler('mixr', adjustmentType('channel mixer'), (reader, target, left) => {
|
|
2855
2826
|
if (readUint16(reader) !== 1)
|
|
2856
2827
|
throw new Error('Invalid mixr version');
|
|
2857
|
-
|
|
2828
|
+
const adjustment = target.adjustment = Object.assign(Object.assign({}, target.adjustment), { type: 'channel mixer', monochrome: !!readUint16(reader) });
|
|
2858
2829
|
if (!adjustment.monochrome) {
|
|
2859
2830
|
adjustment.red = readMixrChannel(reader);
|
|
2860
2831
|
adjustment.green = readMixrChannel(reader);
|
|
@@ -2862,8 +2833,8 @@ addHandler('mixr', adjustmentType('channel mixer'), function (reader, target, le
|
|
|
2862
2833
|
}
|
|
2863
2834
|
adjustment.gray = readMixrChannel(reader);
|
|
2864
2835
|
skipBytes(reader, left());
|
|
2865
|
-
},
|
|
2866
|
-
|
|
2836
|
+
}, (writer, target) => {
|
|
2837
|
+
const info = target.adjustment;
|
|
2867
2838
|
writeUint16(writer, 1); // version
|
|
2868
2839
|
writeUint16(writer, info.monochrome ? 1 : 0);
|
|
2869
2840
|
if (info.monochrome) {
|
|
@@ -2877,26 +2848,26 @@ addHandler('mixr', adjustmentType('channel mixer'), function (reader, target, le
|
|
|
2877
2848
|
writeMixrChannel(writer, info.gray);
|
|
2878
2849
|
}
|
|
2879
2850
|
});
|
|
2880
|
-
|
|
2851
|
+
const colorLookupType = createEnum('colorLookupType', '3DLUT', {
|
|
2881
2852
|
'3dlut': '3DLUT',
|
|
2882
2853
|
abstractProfile: 'abstractProfile',
|
|
2883
2854
|
deviceLinkProfile: 'deviceLinkProfile',
|
|
2884
2855
|
});
|
|
2885
|
-
|
|
2856
|
+
const LUTFormatType = createEnum('LUTFormatType', 'look', {
|
|
2886
2857
|
look: 'LUTFormatLOOK',
|
|
2887
2858
|
cube: 'LUTFormatCUBE',
|
|
2888
2859
|
'3dl': 'LUTFormat3DL',
|
|
2889
2860
|
});
|
|
2890
|
-
|
|
2861
|
+
const colorLookupOrder = createEnum('colorLookupOrder', 'rgb', {
|
|
2891
2862
|
rgb: 'rgbOrder',
|
|
2892
2863
|
bgr: 'bgrOrder',
|
|
2893
2864
|
});
|
|
2894
|
-
addHandler('clrL', adjustmentType('color lookup'),
|
|
2865
|
+
addHandler('clrL', adjustmentType('color lookup'), (reader, target, left) => {
|
|
2895
2866
|
if (readUint16(reader) !== 1)
|
|
2896
2867
|
throw new Error('Invalid clrL version');
|
|
2897
|
-
|
|
2868
|
+
const desc = readVersionAndDescriptor(reader);
|
|
2898
2869
|
target.adjustment = { type: 'color lookup' };
|
|
2899
|
-
|
|
2870
|
+
const info = target.adjustment;
|
|
2900
2871
|
if (desc.lookupType !== undefined)
|
|
2901
2872
|
info.lookupType = colorLookupType.decode(desc.lookupType);
|
|
2902
2873
|
if (desc['Nm '] !== undefined)
|
|
@@ -2916,9 +2887,9 @@ addHandler('clrL', adjustmentType('color lookup'), function (reader, target, lef
|
|
|
2916
2887
|
if (desc.LUT3DFileName !== undefined)
|
|
2917
2888
|
info.lut3DFileName = desc.LUT3DFileName;
|
|
2918
2889
|
skipBytes(reader, left());
|
|
2919
|
-
},
|
|
2920
|
-
|
|
2921
|
-
|
|
2890
|
+
}, (writer, target) => {
|
|
2891
|
+
const info = target.adjustment;
|
|
2892
|
+
const desc = {};
|
|
2922
2893
|
if (info.lookupType !== undefined)
|
|
2923
2894
|
desc.lookupType = colorLookupType.encode(info.lookupType);
|
|
2924
2895
|
if (info.name !== undefined)
|
|
@@ -2940,58 +2911,58 @@ addHandler('clrL', adjustmentType('color lookup'), function (reader, target, lef
|
|
|
2940
2911
|
writeUint16(writer, 1); // version
|
|
2941
2912
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
2942
2913
|
});
|
|
2943
|
-
addHandler('nvrt', adjustmentType('invert'),
|
|
2914
|
+
addHandler('nvrt', adjustmentType('invert'), (reader, target, left) => {
|
|
2944
2915
|
target.adjustment = { type: 'invert' };
|
|
2945
2916
|
skipBytes(reader, left());
|
|
2946
|
-
},
|
|
2917
|
+
}, () => {
|
|
2947
2918
|
// nothing to write here
|
|
2948
2919
|
});
|
|
2949
|
-
addHandler('post', adjustmentType('posterize'),
|
|
2920
|
+
addHandler('post', adjustmentType('posterize'), (reader, target, left) => {
|
|
2950
2921
|
target.adjustment = {
|
|
2951
2922
|
type: 'posterize',
|
|
2952
2923
|
levels: readUint16(reader),
|
|
2953
2924
|
};
|
|
2954
2925
|
skipBytes(reader, left());
|
|
2955
|
-
},
|
|
2926
|
+
}, (writer, target) => {
|
|
2956
2927
|
var _a;
|
|
2957
|
-
|
|
2928
|
+
const info = target.adjustment;
|
|
2958
2929
|
writeUint16(writer, (_a = info.levels) !== null && _a !== void 0 ? _a : 4);
|
|
2959
2930
|
writeZeros(writer, 2);
|
|
2960
2931
|
});
|
|
2961
|
-
addHandler('thrs', adjustmentType('threshold'),
|
|
2932
|
+
addHandler('thrs', adjustmentType('threshold'), (reader, target, left) => {
|
|
2962
2933
|
target.adjustment = {
|
|
2963
2934
|
type: 'threshold',
|
|
2964
2935
|
level: readUint16(reader),
|
|
2965
2936
|
};
|
|
2966
2937
|
skipBytes(reader, left());
|
|
2967
|
-
},
|
|
2938
|
+
}, (writer, target) => {
|
|
2968
2939
|
var _a;
|
|
2969
|
-
|
|
2940
|
+
const info = target.adjustment;
|
|
2970
2941
|
writeUint16(writer, (_a = info.level) !== null && _a !== void 0 ? _a : 128);
|
|
2971
2942
|
writeZeros(writer, 2);
|
|
2972
2943
|
});
|
|
2973
|
-
|
|
2974
|
-
addHandler('grdm', adjustmentType('gradient map'),
|
|
2975
|
-
|
|
2944
|
+
const grdmColorModels = ['', '', '', 'rgb', 'hsb', '', 'lab'];
|
|
2945
|
+
addHandler('grdm', adjustmentType('gradient map'), (reader, target, left) => {
|
|
2946
|
+
const version = readUint16(reader);
|
|
2976
2947
|
if (version !== 1 && version !== 3)
|
|
2977
2948
|
throw new Error('Invalid grdm version');
|
|
2978
|
-
|
|
2949
|
+
const info = {
|
|
2979
2950
|
type: 'gradient map',
|
|
2980
2951
|
gradientType: 'solid',
|
|
2981
2952
|
};
|
|
2982
2953
|
info.reverse = !!readUint8(reader);
|
|
2983
2954
|
info.dither = !!readUint8(reader);
|
|
2984
|
-
|
|
2955
|
+
const hasMethod = !!readUint8(reader);
|
|
2985
2956
|
reader.offset--;
|
|
2986
2957
|
if (hasMethod) {
|
|
2987
|
-
|
|
2958
|
+
const method = readSignature(reader);
|
|
2988
2959
|
info.method = gradientInterpolationMethodType.decode(method);
|
|
2989
2960
|
}
|
|
2990
2961
|
info.name = readUnicodeString(reader);
|
|
2991
2962
|
info.colorStops = [];
|
|
2992
2963
|
info.opacityStops = [];
|
|
2993
|
-
|
|
2994
|
-
for (
|
|
2964
|
+
const stopsCount = readUint16(reader);
|
|
2965
|
+
for (let i = 0; i < stopsCount; i++) {
|
|
2995
2966
|
info.colorStops.push({
|
|
2996
2967
|
location: readUint32(reader),
|
|
2997
2968
|
midpoint: readUint32(reader) / 100,
|
|
@@ -2999,20 +2970,20 @@ addHandler('grdm', adjustmentType('gradient map'), function (reader, target, lef
|
|
|
2999
2970
|
});
|
|
3000
2971
|
skipBytes(reader, 2);
|
|
3001
2972
|
}
|
|
3002
|
-
|
|
3003
|
-
for (
|
|
2973
|
+
const opacityStopsCount = readUint16(reader);
|
|
2974
|
+
for (let i = 0; i < opacityStopsCount; i++) {
|
|
3004
2975
|
info.opacityStops.push({
|
|
3005
2976
|
location: readUint32(reader),
|
|
3006
2977
|
midpoint: readUint32(reader) / 100,
|
|
3007
2978
|
opacity: readUint16(reader) / 0xff,
|
|
3008
2979
|
});
|
|
3009
2980
|
}
|
|
3010
|
-
|
|
2981
|
+
const expansionCount = readUint16(reader);
|
|
3011
2982
|
if (expansionCount !== 2)
|
|
3012
2983
|
throw new Error('Invalid grdm expansion count');
|
|
3013
|
-
|
|
2984
|
+
const interpolation = readUint16(reader);
|
|
3014
2985
|
info.smoothness = interpolation / 4096;
|
|
3015
|
-
|
|
2986
|
+
const length = readUint16(reader);
|
|
3016
2987
|
if (length !== 32)
|
|
3017
2988
|
throw new Error('Invalid grdm length');
|
|
3018
2989
|
info.gradientType = readUint16(reader) ? 'noise' : 'solid';
|
|
@@ -3034,18 +3005,14 @@ addHandler('grdm', adjustmentType('gradient map'), function (reader, target, lef
|
|
|
3034
3005
|
readUint16(reader) / 0x8000,
|
|
3035
3006
|
];
|
|
3036
3007
|
skipBytes(reader, left());
|
|
3037
|
-
for (
|
|
3038
|
-
var s = _a[_i];
|
|
3008
|
+
for (const s of info.colorStops)
|
|
3039
3009
|
s.location /= interpolation;
|
|
3040
|
-
|
|
3041
|
-
for (var _b = 0, _c = info.opacityStops; _b < _c.length; _b++) {
|
|
3042
|
-
var s = _c[_b];
|
|
3010
|
+
for (const s of info.opacityStops)
|
|
3043
3011
|
s.location /= interpolation;
|
|
3044
|
-
}
|
|
3045
3012
|
target.adjustment = info;
|
|
3046
|
-
},
|
|
3013
|
+
}, (writer, target) => {
|
|
3047
3014
|
var _a, _b, _c;
|
|
3048
|
-
|
|
3015
|
+
const info = target.adjustment;
|
|
3049
3016
|
writeUint16(writer, info.method !== undefined ? 3 : 1); // version
|
|
3050
3017
|
writeUint8(writer, info.reverse ? 1 : 0);
|
|
3051
3018
|
writeUint8(writer, info.dither ? 1 : 0);
|
|
@@ -3054,17 +3021,15 @@ addHandler('grdm', adjustmentType('gradient map'), function (reader, target, lef
|
|
|
3054
3021
|
}
|
|
3055
3022
|
writeUnicodeStringWithPadding(writer, info.name || '');
|
|
3056
3023
|
writeUint16(writer, info.colorStops && info.colorStops.length || 0);
|
|
3057
|
-
|
|
3058
|
-
for (
|
|
3059
|
-
var s = _d[_i];
|
|
3024
|
+
const interpolation = Math.round(((_a = info.smoothness) !== null && _a !== void 0 ? _a : 1) * 4096);
|
|
3025
|
+
for (const s of info.colorStops || []) {
|
|
3060
3026
|
writeUint32(writer, Math.round(s.location * interpolation));
|
|
3061
3027
|
writeUint32(writer, Math.round(s.midpoint * 100));
|
|
3062
3028
|
writeColor(writer, s.color);
|
|
3063
3029
|
writeZeros(writer, 2);
|
|
3064
3030
|
}
|
|
3065
3031
|
writeUint16(writer, info.opacityStops && info.opacityStops.length || 0);
|
|
3066
|
-
for (
|
|
3067
|
-
var s = _f[_e];
|
|
3032
|
+
for (const s of info.opacityStops || []) {
|
|
3068
3033
|
writeUint32(writer, Math.round(s.location * interpolation));
|
|
3069
3034
|
writeUint32(writer, Math.round(s.midpoint * 100));
|
|
3070
3035
|
writeUint16(writer, Math.round(s.opacity * 0xff));
|
|
@@ -3077,11 +3042,11 @@ addHandler('grdm', adjustmentType('gradient map'), function (reader, target, lef
|
|
|
3077
3042
|
writeUint16(writer, info.addTransparency ? 1 : 0);
|
|
3078
3043
|
writeUint16(writer, info.restrictColors ? 1 : 0);
|
|
3079
3044
|
writeUint32(writer, Math.round(((_b = info.roughness) !== null && _b !== void 0 ? _b : 1) * 4096));
|
|
3080
|
-
|
|
3045
|
+
const colorModel = grdmColorModels.indexOf((_c = info.colorModel) !== null && _c !== void 0 ? _c : 'rgb');
|
|
3081
3046
|
writeUint16(writer, colorModel === -1 ? 3 : colorModel);
|
|
3082
|
-
for (
|
|
3047
|
+
for (let i = 0; i < 4; i++)
|
|
3083
3048
|
writeUint16(writer, Math.round((info.min && info.min[i] || 0) * 0x8000));
|
|
3084
|
-
for (
|
|
3049
|
+
for (let i = 0; i < 4; i++)
|
|
3085
3050
|
writeUint16(writer, Math.round((info.max && info.max[i] || 0) * 0x8000));
|
|
3086
3051
|
writeZeros(writer, 4);
|
|
3087
3052
|
});
|
|
@@ -3094,20 +3059,20 @@ function readSelectiveColors(reader) {
|
|
|
3094
3059
|
};
|
|
3095
3060
|
}
|
|
3096
3061
|
function writeSelectiveColors(writer, cmyk) {
|
|
3097
|
-
|
|
3062
|
+
const c = cmyk || {};
|
|
3098
3063
|
writeInt16(writer, c.c);
|
|
3099
3064
|
writeInt16(writer, c.m);
|
|
3100
3065
|
writeInt16(writer, c.y);
|
|
3101
3066
|
writeInt16(writer, c.k);
|
|
3102
3067
|
}
|
|
3103
|
-
addHandler('selc', adjustmentType('selective color'),
|
|
3068
|
+
addHandler('selc', adjustmentType('selective color'), (reader, target) => {
|
|
3104
3069
|
if (readUint16(reader) !== 1)
|
|
3105
3070
|
throw new Error('Invalid selc version');
|
|
3106
|
-
|
|
3071
|
+
const mode = readUint16(reader) ? 'absolute' : 'relative';
|
|
3107
3072
|
skipBytes(reader, 8);
|
|
3108
3073
|
target.adjustment = {
|
|
3109
3074
|
type: 'selective color',
|
|
3110
|
-
mode
|
|
3075
|
+
mode,
|
|
3111
3076
|
reds: readSelectiveColors(reader),
|
|
3112
3077
|
yellows: readSelectiveColors(reader),
|
|
3113
3078
|
greens: readSelectiveColors(reader),
|
|
@@ -3118,8 +3083,8 @@ addHandler('selc', adjustmentType('selective color'), function (reader, target)
|
|
|
3118
3083
|
neutrals: readSelectiveColors(reader),
|
|
3119
3084
|
blacks: readSelectiveColors(reader),
|
|
3120
3085
|
};
|
|
3121
|
-
},
|
|
3122
|
-
|
|
3086
|
+
}, (writer, target) => {
|
|
3087
|
+
const info = target.adjustment;
|
|
3123
3088
|
writeUint16(writer, 1); // version
|
|
3124
3089
|
writeUint16(writer, info.mode === 'absolute' ? 1 : 0);
|
|
3125
3090
|
writeZeros(writer, 8);
|
|
@@ -3133,26 +3098,26 @@ addHandler('selc', adjustmentType('selective color'), function (reader, target)
|
|
|
3133
3098
|
writeSelectiveColors(writer, info.neutrals);
|
|
3134
3099
|
writeSelectiveColors(writer, info.blacks);
|
|
3135
3100
|
});
|
|
3136
|
-
addHandler('CgEd',
|
|
3137
|
-
|
|
3101
|
+
addHandler('CgEd', target => {
|
|
3102
|
+
const a = target.adjustment;
|
|
3138
3103
|
if (!a)
|
|
3139
3104
|
return false;
|
|
3140
3105
|
return (a.type === 'brightness/contrast' && !a.useLegacy) ||
|
|
3141
3106
|
((a.type === 'levels' || a.type === 'curves' || a.type === 'exposure' || a.type === 'channel mixer' ||
|
|
3142
3107
|
a.type === 'hue/saturation') && a.presetFileName !== undefined);
|
|
3143
|
-
},
|
|
3144
|
-
|
|
3108
|
+
}, (reader, target, left) => {
|
|
3109
|
+
const desc = readVersionAndDescriptor(reader);
|
|
3145
3110
|
if (desc.Vrsn !== 1)
|
|
3146
3111
|
throw new Error('Invalid CgEd version');
|
|
3147
3112
|
// this section can specify preset file name for other adjustment types
|
|
3148
3113
|
if ('presetFileName' in desc) {
|
|
3149
|
-
target.adjustment =
|
|
3114
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), { presetKind: desc.presetKind, presetFileName: desc.presetFileName });
|
|
3150
3115
|
}
|
|
3151
3116
|
else if ('curvesPresetFileName' in desc) {
|
|
3152
|
-
target.adjustment =
|
|
3117
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), { presetKind: desc.curvesPresetKind, presetFileName: desc.curvesPresetFileName });
|
|
3153
3118
|
}
|
|
3154
3119
|
else if ('mixerPresetFileName' in desc) {
|
|
3155
|
-
target.adjustment =
|
|
3120
|
+
target.adjustment = Object.assign(Object.assign({}, target.adjustment), { presetKind: desc.mixerPresetKind, presetFileName: desc.mixerPresetFileName });
|
|
3156
3121
|
}
|
|
3157
3122
|
else {
|
|
3158
3123
|
target.adjustment = {
|
|
@@ -3166,11 +3131,11 @@ addHandler('CgEd', function (target) {
|
|
|
3166
3131
|
};
|
|
3167
3132
|
}
|
|
3168
3133
|
skipBytes(reader, left());
|
|
3169
|
-
},
|
|
3134
|
+
}, (writer, target) => {
|
|
3170
3135
|
var _a, _b, _c, _d;
|
|
3171
|
-
|
|
3136
|
+
const info = target.adjustment;
|
|
3172
3137
|
if (info.type === 'levels' || info.type === 'exposure' || info.type === 'hue/saturation') {
|
|
3173
|
-
|
|
3138
|
+
const desc = {
|
|
3174
3139
|
Vrsn: 1,
|
|
3175
3140
|
presetKind: (_a = info.presetKind) !== null && _a !== void 0 ? _a : 1,
|
|
3176
3141
|
presetFileName: info.presetFileName || '',
|
|
@@ -3178,7 +3143,7 @@ addHandler('CgEd', function (target) {
|
|
|
3178
3143
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
3179
3144
|
}
|
|
3180
3145
|
else if (info.type === 'curves') {
|
|
3181
|
-
|
|
3146
|
+
const desc = {
|
|
3182
3147
|
Vrsn: 1,
|
|
3183
3148
|
curvesPresetKind: (_b = info.presetKind) !== null && _b !== void 0 ? _b : 1,
|
|
3184
3149
|
curvesPresetFileName: info.presetFileName || '',
|
|
@@ -3186,7 +3151,7 @@ addHandler('CgEd', function (target) {
|
|
|
3186
3151
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
3187
3152
|
}
|
|
3188
3153
|
else if (info.type === 'channel mixer') {
|
|
3189
|
-
|
|
3154
|
+
const desc = {
|
|
3190
3155
|
Vrsn: 1,
|
|
3191
3156
|
mixerPresetKind: (_c = info.presetKind) !== null && _c !== void 0 ? _c : 1,
|
|
3192
3157
|
mixerPresetFileName: info.presetFileName || '',
|
|
@@ -3194,7 +3159,7 @@ addHandler('CgEd', function (target) {
|
|
|
3194
3159
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
3195
3160
|
}
|
|
3196
3161
|
else if (info.type === 'brightness/contrast') {
|
|
3197
|
-
|
|
3162
|
+
const desc = {
|
|
3198
3163
|
Vrsn: 1,
|
|
3199
3164
|
Brgh: info.brightness || 0,
|
|
3200
3165
|
Cntr: info.contrast || 0,
|
|
@@ -3210,12 +3175,11 @@ addHandler('CgEd', function (target) {
|
|
|
3210
3175
|
}
|
|
3211
3176
|
});
|
|
3212
3177
|
function getTextLayersSortedByIndex(psd) {
|
|
3213
|
-
|
|
3178
|
+
const layers = [];
|
|
3214
3179
|
function collect(layer) {
|
|
3215
3180
|
var _a;
|
|
3216
3181
|
if (layer.children) {
|
|
3217
|
-
for (
|
|
3218
|
-
var child = _b[_i];
|
|
3182
|
+
for (const child of layer.children) {
|
|
3219
3183
|
if (((_a = child.text) === null || _a === void 0 ? void 0 : _a.index) !== undefined) {
|
|
3220
3184
|
layers[child.text.index] = child;
|
|
3221
3185
|
}
|
|
@@ -3226,16 +3190,16 @@ function getTextLayersSortedByIndex(psd) {
|
|
|
3226
3190
|
collect(psd);
|
|
3227
3191
|
return layers;
|
|
3228
3192
|
}
|
|
3229
|
-
addHandler('Txt2', hasKey('engineData'),
|
|
3230
|
-
|
|
3193
|
+
addHandler('Txt2', hasKey('engineData'), (reader, target, left, psd) => {
|
|
3194
|
+
const data = readBytes(reader, left());
|
|
3231
3195
|
target.engineData = fromByteArray(data);
|
|
3232
|
-
|
|
3233
|
-
|
|
3234
|
-
|
|
3235
|
-
|
|
3196
|
+
const layersByIndex = getTextLayersSortedByIndex(psd);
|
|
3197
|
+
const engineData = parseEngineData(data);
|
|
3198
|
+
const engineData2 = decodeEngineData2(engineData);
|
|
3199
|
+
const TextFrameSet = engineData2.ResourceDict.TextFrameSet;
|
|
3236
3200
|
if (TextFrameSet) {
|
|
3237
|
-
for (
|
|
3238
|
-
|
|
3201
|
+
for (let i = 0; i < TextFrameSet.length; i++) {
|
|
3202
|
+
const layer = layersByIndex[i];
|
|
3239
3203
|
if (TextFrameSet[i].path && (layer === null || layer === void 0 ? void 0 : layer.text)) {
|
|
3240
3204
|
layer.text.textPath = TextFrameSet[i].path;
|
|
3241
3205
|
}
|
|
@@ -3245,94 +3209,93 @@ addHandler('Txt2', hasKey('engineData'), function (reader, target, left, psd) {
|
|
|
3245
3209
|
// require('fs').writeFileSync('test_data.bin', data);
|
|
3246
3210
|
// require('fs').writeFileSync('test_data.txt', require('util').inspect(engineData, false, 99, false), 'utf8');
|
|
3247
3211
|
// require('fs').writeFileSync('test_data.json', JSON.stringify(engineData2, null, 2), 'utf8');
|
|
3248
|
-
},
|
|
3249
|
-
|
|
3212
|
+
}, (writer, target) => {
|
|
3213
|
+
const buffer = toByteArray(target.engineData);
|
|
3250
3214
|
writeBytes(writer, buffer);
|
|
3251
3215
|
});
|
|
3252
|
-
addHandler('FEid', hasKey('filterEffectsMasks'),
|
|
3253
|
-
|
|
3216
|
+
addHandler('FEid', hasKey('filterEffectsMasks'), (reader, target, leftBytes) => {
|
|
3217
|
+
const version = readInt32(reader);
|
|
3254
3218
|
if (version < 1 || version > 3)
|
|
3255
|
-
throw new Error(
|
|
3219
|
+
throw new Error(`Invalid filterEffects version ${version}`);
|
|
3256
3220
|
target.filterEffectsMasks = [];
|
|
3257
3221
|
while (leftBytes() > 8) {
|
|
3258
3222
|
if (readUint32(reader))
|
|
3259
3223
|
throw new Error('filterEffects: 64 bit length is not supported');
|
|
3260
|
-
|
|
3261
|
-
|
|
3262
|
-
|
|
3263
|
-
|
|
3224
|
+
const length = readUint32(reader);
|
|
3225
|
+
const end = reader.offset + length;
|
|
3226
|
+
const id = readPascalString(reader, 1);
|
|
3227
|
+
const effectVersion = readInt32(reader);
|
|
3264
3228
|
if (effectVersion !== 1)
|
|
3265
|
-
throw new Error(
|
|
3229
|
+
throw new Error(`Invalid filterEffect version ${effectVersion}`);
|
|
3266
3230
|
if (readUint32(reader))
|
|
3267
3231
|
throw new Error('filterEffect: 64 bit length is not supported');
|
|
3268
3232
|
/*const effectLength =*/ readUint32(reader);
|
|
3269
3233
|
// const endOfEffect = reader.offset + effectLength;
|
|
3270
|
-
|
|
3271
|
-
|
|
3272
|
-
|
|
3273
|
-
|
|
3274
|
-
|
|
3275
|
-
|
|
3276
|
-
|
|
3234
|
+
const top = readInt32(reader);
|
|
3235
|
+
const left = readInt32(reader);
|
|
3236
|
+
const bottom = readInt32(reader);
|
|
3237
|
+
const right = readInt32(reader);
|
|
3238
|
+
const depth = readInt32(reader);
|
|
3239
|
+
const maxChannels = readInt32(reader);
|
|
3240
|
+
const channels = [];
|
|
3277
3241
|
// 0 -> R, 1 -> G, 2 -> B, 25 -> A
|
|
3278
|
-
for (
|
|
3279
|
-
|
|
3242
|
+
for (let i = 0; i < (maxChannels + 2); i++) { // channels + user mask + sheet mask
|
|
3243
|
+
const exists = readInt32(reader);
|
|
3280
3244
|
if (exists) {
|
|
3281
3245
|
if (readUint32(reader))
|
|
3282
3246
|
throw new Error('filterEffect: 64 bit length is not supported');
|
|
3283
|
-
|
|
3247
|
+
const channelLength = readUint32(reader);
|
|
3284
3248
|
if (!channelLength)
|
|
3285
3249
|
throw new Error('filterEffect: Empty channel');
|
|
3286
|
-
|
|
3287
|
-
|
|
3288
|
-
channels.push({ compressionMode
|
|
3250
|
+
const compressionMode = readUint16(reader);
|
|
3251
|
+
const data = readBytes(reader, channelLength - 2);
|
|
3252
|
+
channels.push({ compressionMode, data });
|
|
3289
3253
|
}
|
|
3290
3254
|
else {
|
|
3291
3255
|
channels.push(undefined);
|
|
3292
3256
|
}
|
|
3293
3257
|
}
|
|
3294
|
-
target.filterEffectsMasks.push({ id
|
|
3258
|
+
target.filterEffectsMasks.push({ id, top, left, bottom, right, depth, channels });
|
|
3295
3259
|
if (reader.offset < end && readUint8(reader)) {
|
|
3296
|
-
|
|
3297
|
-
|
|
3298
|
-
|
|
3299
|
-
|
|
3260
|
+
const top = readInt32(reader);
|
|
3261
|
+
const left = readInt32(reader);
|
|
3262
|
+
const bottom = readInt32(reader);
|
|
3263
|
+
const right = readInt32(reader);
|
|
3300
3264
|
if (readUint32(reader))
|
|
3301
3265
|
throw new Error('filterEffect: 64 bit length is not supported');
|
|
3302
|
-
|
|
3303
|
-
|
|
3304
|
-
|
|
3305
|
-
target.filterEffectsMasks[target.filterEffectsMasks.length - 1].extra = { top
|
|
3266
|
+
const extraLength = readUint32(reader);
|
|
3267
|
+
const compressionMode = readUint16(reader);
|
|
3268
|
+
const data = readBytes(reader, extraLength - 2);
|
|
3269
|
+
target.filterEffectsMasks[target.filterEffectsMasks.length - 1].extra = { top, left, bottom, right, compressionMode, data };
|
|
3306
3270
|
}
|
|
3307
3271
|
reader.offset = end;
|
|
3308
|
-
|
|
3272
|
+
let len = length;
|
|
3309
3273
|
while (len % 4) {
|
|
3310
3274
|
reader.offset++;
|
|
3311
3275
|
len++;
|
|
3312
3276
|
}
|
|
3313
3277
|
}
|
|
3314
|
-
},
|
|
3278
|
+
}, (writer, target) => {
|
|
3315
3279
|
var _a;
|
|
3316
3280
|
writeInt32(writer, 3); // version
|
|
3317
|
-
for (
|
|
3318
|
-
var mask = _b[_i];
|
|
3281
|
+
for (const mask of target.filterEffectsMasks) {
|
|
3319
3282
|
writeUint32(writer, 0);
|
|
3320
3283
|
writeUint32(writer, 0);
|
|
3321
|
-
|
|
3284
|
+
const lengthOffset = writer.offset;
|
|
3322
3285
|
writePascalString(writer, mask.id, 1);
|
|
3323
3286
|
writeInt32(writer, 1); // version
|
|
3324
3287
|
writeUint32(writer, 0);
|
|
3325
3288
|
writeUint32(writer, 0);
|
|
3326
|
-
|
|
3289
|
+
const length2Offset = writer.offset;
|
|
3327
3290
|
writeInt32(writer, mask.top);
|
|
3328
3291
|
writeInt32(writer, mask.left);
|
|
3329
3292
|
writeInt32(writer, mask.bottom);
|
|
3330
3293
|
writeInt32(writer, mask.right);
|
|
3331
3294
|
writeInt32(writer, mask.depth);
|
|
3332
|
-
|
|
3295
|
+
const maxChannels = Math.max(0, mask.channels.length - 2);
|
|
3333
3296
|
writeInt32(writer, maxChannels);
|
|
3334
|
-
for (
|
|
3335
|
-
|
|
3297
|
+
for (let i = 0; i < (maxChannels + 2); i++) {
|
|
3298
|
+
const channel = mask.channels[i];
|
|
3336
3299
|
writeInt32(writer, channel ? 1 : 0);
|
|
3337
3300
|
if (channel) {
|
|
3338
3301
|
writeUint32(writer, 0);
|
|
@@ -3342,7 +3305,7 @@ addHandler('FEid', hasKey('filterEffectsMasks'), function (reader, target, leftB
|
|
|
3342
3305
|
}
|
|
3343
3306
|
}
|
|
3344
3307
|
writer.view.setUint32(length2Offset - 4, writer.offset - length2Offset, false);
|
|
3345
|
-
|
|
3308
|
+
const extra = (_a = target.filterEffectsMasks[target.filterEffectsMasks.length - 1]) === null || _a === void 0 ? void 0 : _a.extra;
|
|
3346
3309
|
if (extra) {
|
|
3347
3310
|
writeUint8(writer, 1);
|
|
3348
3311
|
writeInt32(writer, extra.top);
|
|
@@ -3354,29 +3317,29 @@ addHandler('FEid', hasKey('filterEffectsMasks'), function (reader, target, leftB
|
|
|
3354
3317
|
writeUint16(writer, extra.compressionMode);
|
|
3355
3318
|
writeBytes(writer, extra.data);
|
|
3356
3319
|
}
|
|
3357
|
-
|
|
3358
|
-
writer.view.setUint32(lengthOffset - 4,
|
|
3359
|
-
while (
|
|
3320
|
+
let length = writer.offset - lengthOffset;
|
|
3321
|
+
writer.view.setUint32(lengthOffset - 4, length, false);
|
|
3322
|
+
while (length % 4) {
|
|
3360
3323
|
writeZeros(writer, 1);
|
|
3361
|
-
|
|
3324
|
+
length++;
|
|
3362
3325
|
}
|
|
3363
3326
|
}
|
|
3364
3327
|
});
|
|
3365
3328
|
addHandlerAlias('FXid', 'FEid');
|
|
3366
|
-
addHandler('FMsk', hasKey('filterMask'),
|
|
3329
|
+
addHandler('FMsk', hasKey('filterMask'), (reader, target) => {
|
|
3367
3330
|
target.filterMask = {
|
|
3368
3331
|
colorSpace: readColor(reader),
|
|
3369
3332
|
opacity: readUint16(reader) / 0xff,
|
|
3370
3333
|
};
|
|
3371
|
-
},
|
|
3334
|
+
}, (writer, target) => {
|
|
3372
3335
|
var _a;
|
|
3373
3336
|
writeColor(writer, target.filterMask.colorSpace);
|
|
3374
3337
|
writeUint16(writer, clamp((_a = target.filterMask.opacity) !== null && _a !== void 0 ? _a : 1, 0, 1) * 0xff);
|
|
3375
3338
|
});
|
|
3376
3339
|
addHandler('artd', // document-wide artboard info
|
|
3377
|
-
|
|
3378
|
-
target
|
|
3379
|
-
|
|
3340
|
+
// document-wide artboard info
|
|
3341
|
+
target => target.artboards !== undefined, (reader, target, left) => {
|
|
3342
|
+
const desc = readVersionAndDescriptor(reader);
|
|
3380
3343
|
target.artboards = {
|
|
3381
3344
|
count: desc['Cnt '],
|
|
3382
3345
|
autoExpandOffset: { horizontal: desc.autoExpandOffset.Hrzn, vertical: desc.autoExpandOffset.Vrtc },
|
|
@@ -3389,10 +3352,10 @@ target) { return target.artboards !== undefined; }, function (reader, target, le
|
|
|
3389
3352
|
docDefaultNewArtboardBackgroundType: desc.docDefaultNewArtboardBackgroundType,
|
|
3390
3353
|
};
|
|
3391
3354
|
skipBytes(reader, left());
|
|
3392
|
-
},
|
|
3355
|
+
}, (writer, target) => {
|
|
3393
3356
|
var _a, _b, _c, _d, _e;
|
|
3394
|
-
|
|
3395
|
-
|
|
3357
|
+
const artb = target.artboards;
|
|
3358
|
+
const desc = {
|
|
3396
3359
|
'Cnt ': artb.count,
|
|
3397
3360
|
autoExpandOffset: artb.autoExpandOffset ? { Hrzn: artb.autoExpandOffset.horizontal, Vrtc: artb.autoExpandOffset.vertical } : { Hrzn: 0, Vrtc: 0 },
|
|
3398
3361
|
origin: artb.origin ? { Hrzn: artb.origin.horizontal, Vrtc: artb.origin.vertical } : { Hrzn: 0, Vrtc: 0 },
|
|
@@ -3406,26 +3369,26 @@ target) { return target.artboards !== undefined; }, function (reader, target, le
|
|
|
3406
3369
|
writeVersionAndDescriptor(writer, '', 'null', desc, 'artd');
|
|
3407
3370
|
});
|
|
3408
3371
|
export function hasMultiEffects(effects) {
|
|
3409
|
-
return Object.keys(effects).map(
|
|
3372
|
+
return Object.keys(effects).map(key => effects[key]).some(v => Array.isArray(v) && v.length > 1);
|
|
3410
3373
|
}
|
|
3411
|
-
addHandler('lfx2',
|
|
3412
|
-
|
|
3374
|
+
addHandler('lfx2', target => target.effects !== undefined && !hasMultiEffects(target.effects), (reader, target, left) => {
|
|
3375
|
+
const version = readUint32(reader);
|
|
3413
3376
|
if (version !== 0)
|
|
3414
|
-
throw new Error(
|
|
3415
|
-
|
|
3377
|
+
throw new Error(`Invalid lfx2 version`);
|
|
3378
|
+
const desc = readVersionAndDescriptor(reader);
|
|
3416
3379
|
// console.log('READ', require('util').inspect(desc, false, 99, true));
|
|
3417
3380
|
// TODO: don't discard if we got it from lmfx
|
|
3418
3381
|
// discard if read in 'lrFX' section
|
|
3419
3382
|
target.effects = parseEffects(desc, !!reader.logMissingFeatures);
|
|
3420
3383
|
skipBytes(reader, left());
|
|
3421
|
-
},
|
|
3422
|
-
|
|
3384
|
+
}, (writer, target, _, options) => {
|
|
3385
|
+
const desc = serializeEffects(target.effects, !!options.logMissingFeatures, true);
|
|
3423
3386
|
// console.log('WRITE', require('util').inspect(desc, false, 99, true));
|
|
3424
3387
|
writeUint32(writer, 0); // version
|
|
3425
3388
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
3426
3389
|
});
|
|
3427
|
-
addHandler('cinf', hasKey('compositorUsed'),
|
|
3428
|
-
|
|
3390
|
+
addHandler('cinf', hasKey('compositorUsed'), (reader, target, left) => {
|
|
3391
|
+
const desc = readVersionAndDescriptor(reader);
|
|
3429
3392
|
// console.log(require('util').inspect(desc, false, 99, true));
|
|
3430
3393
|
function enumValue(desc) {
|
|
3431
3394
|
return desc.split('.')[1];
|
|
@@ -3450,61 +3413,60 @@ addHandler('cinf', hasKey('compositorUsed'), function (reader, target, left) {
|
|
|
3450
3413
|
if (desc.compCoreGPUSupport)
|
|
3451
3414
|
target.compositorUsed.compCoreGPUSupport = enumValue(desc.compCoreGPUSupport);
|
|
3452
3415
|
skipBytes(reader, left());
|
|
3453
|
-
},
|
|
3454
|
-
|
|
3455
|
-
|
|
3416
|
+
}, (writer, target) => {
|
|
3417
|
+
const cinf = target.compositorUsed;
|
|
3418
|
+
const desc = {
|
|
3456
3419
|
Vrsn: cinf.version || { major: 1, minor: 0, fix: 0 },
|
|
3457
3420
|
};
|
|
3458
3421
|
if (cinf.photoshopVersion)
|
|
3459
3422
|
desc.psVersion = cinf.photoshopVersion;
|
|
3460
3423
|
desc.description = cinf.description;
|
|
3461
3424
|
desc.reason = cinf.reason;
|
|
3462
|
-
desc.Engn =
|
|
3425
|
+
desc.Engn = `Engn.${cinf.engine}`;
|
|
3463
3426
|
if (cinf.enableCompCore)
|
|
3464
|
-
desc.enableCompCore =
|
|
3427
|
+
desc.enableCompCore = `enable.${cinf.enableCompCore}`;
|
|
3465
3428
|
if (cinf.enableCompCoreGPU)
|
|
3466
|
-
desc.enableCompCoreGPU =
|
|
3429
|
+
desc.enableCompCoreGPU = `enable.${cinf.enableCompCoreGPU}`;
|
|
3467
3430
|
if (cinf.enableCompCoreThreads)
|
|
3468
|
-
desc.enableCompCoreThreads =
|
|
3431
|
+
desc.enableCompCoreThreads = `enable.${cinf.enableCompCoreThreads}`;
|
|
3469
3432
|
if (cinf.compCoreSupport)
|
|
3470
|
-
desc.compCoreSupport =
|
|
3433
|
+
desc.compCoreSupport = `reason.${cinf.compCoreSupport}`;
|
|
3471
3434
|
if (cinf.compCoreGPUSupport)
|
|
3472
|
-
desc.compCoreGPUSupport =
|
|
3435
|
+
desc.compCoreGPUSupport = `reason.${cinf.compCoreGPUSupport}`;
|
|
3473
3436
|
writeVersionAndDescriptor(writer, '', 'null', desc);
|
|
3474
3437
|
});
|
|
3475
3438
|
// extension settings ?, ignore it
|
|
3476
|
-
addHandler('extn',
|
|
3477
|
-
|
|
3439
|
+
addHandler('extn', target => target._extn !== undefined, (reader, target) => {
|
|
3440
|
+
const desc = readVersionAndDescriptor(reader);
|
|
3478
3441
|
// console.log(require('util').inspect(desc, false, 99, true));
|
|
3479
3442
|
if (MOCK_HANDLERS)
|
|
3480
3443
|
target._extn = desc;
|
|
3481
|
-
},
|
|
3444
|
+
}, (writer, target) => {
|
|
3482
3445
|
// TODO: need to add correct types for desc fields (resources/src.psd)
|
|
3483
3446
|
if (MOCK_HANDLERS)
|
|
3484
3447
|
writeVersionAndDescriptor(writer, '', 'null', target._extn);
|
|
3485
3448
|
});
|
|
3486
|
-
addHandler('iOpa', hasKey('fillOpacity'),
|
|
3449
|
+
addHandler('iOpa', hasKey('fillOpacity'), (reader, target) => {
|
|
3487
3450
|
target.fillOpacity = readUint8(reader) / 0xff;
|
|
3488
3451
|
skipBytes(reader, 3);
|
|
3489
|
-
},
|
|
3452
|
+
}, (writer, target) => {
|
|
3490
3453
|
writeUint8(writer, target.fillOpacity * 0xff);
|
|
3491
3454
|
writeZeros(writer, 3);
|
|
3492
3455
|
});
|
|
3493
|
-
addHandler('brst', hasKey('channelBlendingRestrictions'),
|
|
3456
|
+
addHandler('brst', hasKey('channelBlendingRestrictions'), (reader, target, left) => {
|
|
3494
3457
|
target.channelBlendingRestrictions = [];
|
|
3495
3458
|
while (left() > 4) {
|
|
3496
3459
|
target.channelBlendingRestrictions.push(readInt32(reader));
|
|
3497
3460
|
}
|
|
3498
|
-
},
|
|
3499
|
-
for (
|
|
3500
|
-
var channel = _a[_i];
|
|
3461
|
+
}, (writer, target) => {
|
|
3462
|
+
for (const channel of target.channelBlendingRestrictions) {
|
|
3501
3463
|
writeInt32(writer, channel);
|
|
3502
3464
|
}
|
|
3503
3465
|
});
|
|
3504
|
-
addHandler('tsly', hasKey('transparencyShapesLayer'),
|
|
3466
|
+
addHandler('tsly', hasKey('transparencyShapesLayer'), (reader, target) => {
|
|
3505
3467
|
target.transparencyShapesLayer = !!readUint8(reader);
|
|
3506
3468
|
skipBytes(reader, 3);
|
|
3507
|
-
},
|
|
3469
|
+
}, (writer, target) => {
|
|
3508
3470
|
writeUint8(writer, target.transparencyShapesLayer ? 1 : 0);
|
|
3509
3471
|
writeZeros(writer, 3);
|
|
3510
3472
|
});
|