I'm trying to convert PSD path records to SVG Path data.
Since I don't want to cross post I'll link to the original question. Anyone who wants to copy in the relevant data can copy it back here.
Basically, I get the PSD, parse it, and get the shape information from vector mask object.
It contains an array called paths
that what look to be points shown below:
_ = require 'lodash'
# A path record describes a single point in a vector path. This is used
# in a couple of different places, but most notably in vector shapes.
module.exports = class PathRecord
constructor: (@file) ->
@recordType = null
parse: ->
@recordType = @file.readShort()
switch @recordType
when 0, 3 then @_readPathRecord()
when 1, 2, 4, 5 then @_readBezierPoint()
when 7 then @_readClipboardRecord()
when 8 then @_readInitialFill()
else @file.seek(24, true)
export: ->
_.merge { recordType: @recordType }, switch @recordType
when 0, 3 then { numPoints: @numPoints }
when 1, 2, 4, 5
linked: @linked
closed: (@recordType in [1, 2])
preceding:
vert: @precedingVert
horiz: @precedingHoriz
anchor:
vert: @anchorVert
horiz: @anchorHoriz
leaving:
vert: @leavingVert
horiz: @leavingHoriz
when 7
clipboard:
top: @clipboardTop
left: @clipboardLeft
bottom: @clipboardBottom
right: @clipboardRight
resolution: @clipboardResolution
when 8 then { initialFill: @initialFill }
else {}
isBezierPoint: -> @recordType in [1, 2, 4, 5]
_readPathRecord: ->
@numPoints = @file.readShort()
@file.seek 22, true
_readBezierPoint: ->
@linked = @recordType in [1, 4]
@precedingVert = @file.readPathNumber()
@precedingHoriz = @file.readPathNumber()
@anchorVert = @file.readPathNumber()
@anchorHoriz = @file.readPathNumber()
@leavingVert = @file.readPathNumber()
@leavingHoriz = @file.readPathNumber()
_readClipboardRecord: ->
@clipboardTop = @file.readPathNumber()
@clipboardLeft = @file.readPathNumber()
@clipboardBottom = @file.readPathNumber()
@clipboardRight = @file.readPathNumber()
@clipboardResolution = @file.readPathNumber()
@file.seek 4, true
_readInitialFill: ->
@initialFill = @file.readShort()
@file.seek 22, true
I'm trying to convert that info into SVG path data but I am stuck at two points. What record relates to what path command and the data seems to be values less than 1.
Here is example path data for the Tiger shape you can create in Photoshop:
I've trimmed the data
[
{
"recordType": 6
},
{
"recordType": 8,
"initialFill": 0
},
{
"recordType": 0,
"numPoints": 257
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.14081686735153198,
"horiz": 0.07748442888259888
},
"anchor": {
"vert": 0.14081686735153198,
"horiz": 0.0777387022972107
},
"leaving": {
"vert": 0.13936221599578857,
"horiz": 0.0777667760848999
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.13929903507232666,
"horiz": 0.07793217897415161
},
"anchor": {
"vert": 0.1385088562965393,
"horiz": 0.07837295532226562
},
"leaving": {
"vert": 0.13777965307235718,
"horiz": 0.07837295532226562
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.13706856966018677,
"horiz": 0.07837295532226562
},
"anchor": {
"vert": 0.13632577657699585,
"horiz": 0.07837295532226562
},
"leaving": {
"vert": 0.1364198923110962,
"horiz": 0.07855236530303955
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.13649815320968628,
"horiz": 0.07873183488845825
},
"anchor": {
"vert": 0.13657790422439575,
"horiz": 0.07890427112579346
},
"leaving": {
"vert": 0.1359773874282837,
"horiz": 0.07879406213760376
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.13536030054092407,
"horiz": 0.07869088649749756
},
"anchor": {
"vert": 0.1347590684890747,
"horiz": 0.07858771085739136
},
"leaving": {
"vert": 0.13486969470977783,
"horiz": 0.07879406213760376
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.13499760627746582,
"horiz": 0.07900881767272949
},
"anchor": {
"vert": 0.13512402772903442,
"horiz": 0.07922220230102539
},
"leaving": {
"vert": 0.1344437599182129,
"horiz": 0.07920092344284058
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.1268816590309143,
"horiz": 0.08006417751312256
},
"anchor": {
"vert": 0.12613815069198608,
"horiz": 0.08038073778152466
},
"leaving": {
"vert": 0.12613815069198608,
"horiz": 0.08055287599563599
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.12613815069198608,
"horiz": 0.08073228597640991
},
"anchor": {
"vert": 0.12613815069198608,
"horiz": 0.08091175556182861
},
"leaving": {
"vert": 0.1256791353225708,
"horiz": 0.0807945728302002
}
},
{
"recordType": 2,
"linked": false,
"closed": true,
"preceding": {
"vert": 0.12177199125289917,
"horiz": 0.08080857992172241
},
"anchor": {
"vert": 0.12177199125289917,
"horiz": 0.08080857992172241
},
"leaving": {
"vert": 0.12169301509857178,
"horiz": 0.08107715845108032
}
}
]
The post on github has the function that is parsing the data.