Fix LinearGradient PAD spread mode

This commit is contained in:
DataHoarder 2023-11-29 01:04:52 +01:00
parent 42df53898d
commit 211ae1bdf9
Signed by: DataHoarder
SSH key fingerprint: SHA256:OLTRf6Fl87G52SiR7sWLGNzlJt4WOX+tfI2yxo0z7xk
20 changed files with 236 additions and 106 deletions

View file

@ -264,7 +264,7 @@ func ContainerTagFromPathEntry(path shapes.DrawPath, clip *shapes.ClipPath, colo
//TODO: this is broken
translationTransform := math.TranslateTransform(matrixTransform.GetTranslation().Multiply(-1))
path = shapes.DrawPath{
Style: path.Style,
Style: path.Style, //TODO: apply transform to Style?
Shape: clip.ApplyMatrixTransform(translationTransform, true).ClipShape(path.Shape, true),
}
}

View file

@ -490,7 +490,7 @@ func (p *SWFTreeProcessor) process(actions ActionList) (tag swftag.Tag, newActio
colorTransform = t
}
transform := math.MatrixTransformFromSWF(node.Matrix)
transform := math.MatrixTransformFromSWF(node.Matrix, 1)
p.placeObject(object, placeObjectData{
Action: ActionPlace,
@ -514,7 +514,7 @@ func (p *SWFTreeProcessor) process(actions ActionList) (tag swftag.Tag, newActio
Depth: node.Depth,
ClipDepth: SomeWith(node.ClipDepth, node.Flag.HasClipDepth),
Ratio: SomeWith(float64(node.Ratio)/math2.MaxUint16, node.Flag.HasRatio),
Transform: SomeWith(math.MatrixTransformFromSWF(node.Matrix), node.Flag.HasMatrix),
Transform: SomeWith(math.MatrixTransformFromSWF(node.Matrix, 1), node.Flag.HasMatrix),
ColorTransform: SomeWith(math.ColorTransformFromSWFAlpha(node.ColorTransform), node.Flag.HasColorTransform),
Visible: None[bool](),
})
@ -532,7 +532,7 @@ func (p *SWFTreeProcessor) process(actions ActionList) (tag swftag.Tag, newActio
Depth: node.Depth,
ClipDepth: SomeWith(node.ClipDepth, node.Flag.HasClipDepth),
Ratio: SomeWith(float64(node.Ratio)/math2.MaxUint16, node.Flag.HasRatio),
Transform: SomeWith(math.MatrixTransformFromSWF(node.Matrix), node.Flag.HasMatrix),
Transform: SomeWith(math.MatrixTransformFromSWF(node.Matrix, 1), node.Flag.HasMatrix),
ColorTransform: SomeWith(math.ColorTransformFromSWFAlpha(node.ColorTransform), node.Flag.HasColorTransform),
Visible: SomeWith(node.Visible > 0, node.Flag.HasVisible),
BlendMode: SomeWith(node.BlendMode, node.Flag.HasBlendMode),

View file

@ -194,10 +194,10 @@ func (m MatrixTransform) String() string {
return fmt.Sprintf("%#v", mat.Formatted(m.matrix, mat.FormatPython()))
}
func MatrixTransformFromSWF(m types.MATRIX) MatrixTransform {
func MatrixTransformFromSWF(m types.MATRIX, scale float64) MatrixTransform {
return NewMatrixTransform(
NewVector2(m.ScaleX.Float64(), m.ScaleY.Float64()),
NewVector2(m.RotateSkew0.Float64(), m.RotateSkew1.Float64()),
NewVector2(m.TranslateX.Float64(), m.TranslateY.Float64()),
)
).Multiply(ScaleTransform(NewVector2(scale, scale)))
}

View file

@ -116,6 +116,14 @@ func (v Vector2[T]) Normals() (a, b Vector2[T]) {
}
}
func (v Vector2[T]) Max(b Vector2[T]) Vector2[T] {
return NewVector2(max(v.X, b.X), max(v.Y, b.Y))
}
func (v Vector2[T]) Min(b Vector2[T]) Vector2[T] {
return NewVector2(min(v.X, b.X), min(v.Y, b.Y))
}
func (v Vector2[T]) Abs() Vector2[T] {
x := v.X
if x < 0 {

View file

@ -32,10 +32,10 @@ func (r CubicCurveRecord) Reverse() Record {
func (r CubicCurveRecord) ApplyMatrixTransform(transform math2.MatrixTransform, applyTranslation bool) Record {
//TODO: see how accurate this is
return CubicCurveRecord{
Control1: math2.MatrixTransformApplyToVector(transform, r.Control1, applyTranslation),
Control2: math2.MatrixTransformApplyToVector(transform, r.Control2, applyTranslation),
Anchor: math2.MatrixTransformApplyToVector(transform, r.Anchor, applyTranslation),
Start: math2.MatrixTransformApplyToVector(transform, r.Start, applyTranslation),
Control1: transform.ApplyToVector(r.Control1, applyTranslation),
Control2: transform.ApplyToVector(r.Control2, applyTranslation),
Anchor: transform.ApplyToVector(r.Anchor, applyTranslation),
Start: transform.ApplyToVector(r.Start, applyTranslation),
}
}
@ -59,6 +59,10 @@ func (r CubicCurveRecord) String() string {
return fmt.Sprintf("c %s %s %s", r.Control1, r.Control2, r.Anchor)
}
func (r CubicCurveRecord) BoundingBox() (topLeft, bottomRight math2.Vector2[float64]) {
return r.Start.Min(r.Control1).Min(r.Control2).Min(r.Anchor), r.Start.Max(r.Control1).Max(r.Control2).Max(r.Anchor)
}
func CubicCurveFromQuadraticRecord(q QuadraticCurveRecord) CubicCurveRecord {
return CubicCurveRecord{
Control1: q.Start.AddVector(q.Control.Multiply(2)).Divide(3),

View file

@ -43,6 +43,16 @@ func (r CubicSplineCurveRecord) ApplyMatrixTransform(transform math.MatrixTransf
}
}
func (r CubicSplineCurveRecord) BoundingBox() (topLeft, bottomRight math.Vector2[float64]) {
topLeft = r.Start.Min(r.Anchor)
bottomRight = r.Start.Max(r.Anchor)
for _, c := range r.Control {
topLeft = topLeft.Min(c)
bottomRight = bottomRight.Max(c)
}
return
}
func (r CubicSplineCurveRecord) Equals(other Record) bool {
if o, ok := other.(CubicSplineCurveRecord); ok {
return reflect.DeepEqual(r.Control, o.Control) && r.Start == o.Start && r.Anchor == o.Anchor

View file

@ -29,15 +29,11 @@ func (r LineRecord) Delta() math.Vector2[float64] {
return r.To.SubVector(r.Start)
}
func fake2DCross(a, b math.Vector2[float64]) float64 {
return a.X*b.Y - a.Y + b.X
}
func (r LineRecord) ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) Record {
//TODO: see how accurate this is
return LineRecord{
To: math.MatrixTransformApplyToVector(transform, r.To, applyTranslation),
Start: math.MatrixTransformApplyToVector(transform, r.Start, applyTranslation),
To: transform.ApplyToVector(r.To, applyTranslation),
Start: transform.ApplyToVector(r.Start, applyTranslation),
}
}
@ -53,6 +49,10 @@ func (r LineRecord) SameType(other Record) bool {
return ok
}
func (r LineRecord) BoundingBox() (topLeft, bottomRight math.Vector2[float64]) {
return r.Start.Min(r.To), r.Start.Max(r.To)
}
func (r LineRecord) IsFlat() bool {
return true
}

View file

@ -27,8 +27,8 @@ func (r MoveRecord) Reverse() Record {
func (r MoveRecord) ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) Record {
//TODO: see how accurate this is
return MoveRecord{
To: math.MatrixTransformApplyToVector(transform, r.To, applyTranslation),
Start: math.MatrixTransformApplyToVector(transform, r.Start, applyTranslation),
To: transform.ApplyToVector(r.To, applyTranslation),
Start: transform.ApplyToVector(r.Start, applyTranslation),
}
}
@ -44,6 +44,10 @@ func (r MoveRecord) SameType(other Record) bool {
return ok
}
func (r MoveRecord) BoundingBox() (topLeft, bottomRight math.Vector2[float64]) {
return r.Start.Min(r.To), r.Start.Max(r.To)
}
func (r MoveRecord) IsFlat() bool {
return true
}

View file

@ -31,9 +31,9 @@ func (r QuadraticCurveRecord) Reverse() Record {
func (r QuadraticCurveRecord) ApplyMatrixTransform(transform math2.MatrixTransform, applyTranslation bool) Record {
//TODO: see how accurate this is
return QuadraticCurveRecord{
Control: math2.MatrixTransformApplyToVector(transform, r.Control, applyTranslation),
Anchor: math2.MatrixTransformApplyToVector(transform, r.Anchor, applyTranslation),
Start: math2.MatrixTransformApplyToVector(transform, r.Start, applyTranslation),
Control: transform.ApplyToVector(r.Control, applyTranslation),
Anchor: transform.ApplyToVector(r.Anchor, applyTranslation),
Start: transform.ApplyToVector(r.Start, applyTranslation),
}
}
@ -66,6 +66,10 @@ func QuadraticCurveFromLineRecord(l LineRecord) QuadraticCurveRecord {
}
}
func (r QuadraticCurveRecord) BoundingBox() (topLeft, bottomRight math2.Vector2[float64]) {
return r.Start.Min(r.Control).Min(r.Anchor), r.Start.Max(r.Control).Max(r.Anchor)
}
func (r QuadraticCurveRecord) ToLineRecords(scale int64) []Record {
distanceToleranceSquare := math.Pow(0.5/float64(scale), 2)
points := QuadraticRecursiveBezier(nil, BezierCurveAngleTolerance, distanceToleranceSquare, r.Start, r.Control, r.Anchor, 0)

View file

@ -16,6 +16,8 @@ type Record interface {
ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) Record
BoundingBox() (topLeft, bottomRight math.Vector2[float64])
IsFlat() bool
String() string

View file

@ -13,20 +13,27 @@ type Bitmap struct {
func (b Bitmap) ApplyColorTransform(transform math2.ColorTransform) Fillable {
b2 := b
b2.List = b.List.ApplyColorTransform(transform).(DrawPathList)
b2.Transform = b.Transform
return b2
}
func (b Bitmap) ApplyMatrixTransform(transform math2.MatrixTransform, applyTranslation bool) Fillable {
b2 := b
if !applyTranslation {
panic("not supported")
}
b2.Transform = transform.Combine(b2.Transform)
return b2
}
func (b Bitmap) Fill(shape Shape) DrawPathList {
return b.List.ApplyMatrixTransform(b.Transform, true).Fill(shape)
}
func BitmapFillFromSWF(l DrawPathList, transform types.MATRIX) Bitmap {
// shape is already in pixel world, but matrix comes as twip
baseScale := math2.ScaleTransform(math2.NewVector2[float64](1./types.TwipFactor, 1./types.TwipFactor))
return Bitmap{
List: l,
Transform: math2.MatrixTransformFromSWF(transform).Multiply(baseScale),
List: l,
// shape is already in pixel world, but matrix comes as twip
Transform: math2.MatrixTransformFromSWF(transform, 1/types.TwipFactor),
}
}

View file

@ -288,7 +288,7 @@ func ConvertBitmapToDrawPathList(i image.Image) (r DrawPathList) {
scale := math.ScaleTransform(math.NewVector2(ratioX, ratioY))
r2 := r.ApplyMatrixTransform(scale, true)
return r2
return r2.(DrawPathList)
}
var bitmapHeaderJPEG = []byte{0xff, 0xd8}

View file

@ -9,7 +9,7 @@ type DrawPath struct {
func (p DrawPath) ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) (r DrawPath) {
return DrawPath{
Style: p.Style,
Style: p.Style.ApplyMatrixTransform(transform, applyTranslation),
Shape: p.Shape.ApplyMatrixTransform(transform, applyTranslation),
}
}

View file

@ -47,8 +47,8 @@ func (l DrawPathList) ApplyColorTransform(transform math.ColorTransform) Fillabl
return r
}
func (l DrawPathList) ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) (r DrawPathList) {
r = make(DrawPathList, 0, len(l))
func (l DrawPathList) ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) Fillable {
r := make(DrawPathList, 0, len(l))
for i := range l {
r = append(r, l[i].ApplyMatrixTransform(transform, applyTranslation))
}

View file

@ -16,27 +16,27 @@ type Gradient struct {
SpreadMode swfsubtypes.GradientSpreadMode
InterpolationMode swfsubtypes.GradientInterpolationMode
Interpolation func(self Gradient, overlap, blur float64, gradientSlices int) DrawPathList
}
func (g Gradient) GetSpreadMode() swfsubtypes.GradientSpreadMode {
return g.SpreadMode
}
func (g Gradient) GetInterpolationMode() swfsubtypes.GradientInterpolationMode {
return g.InterpolationMode
Interpolation func(self Gradient, overlap, blur float64, gradientSlices int, bb Rectangle[float64]) DrawPathList
}
func (g Gradient) GetItems() []GradientItem {
return g.Records
}
func (g Gradient) GetInterpolatedDrawPaths(overlap, blur float64, gradientSlices int) DrawPathList {
return g.Interpolation(g, overlap, blur, gradientSlices)
func (g Gradient) GetInterpolatedDrawPaths(overlap, blur float64, gradientSlices int, bb Rectangle[float64]) DrawPathList {
return g.Interpolation(g, overlap, blur, gradientSlices, bb).ApplyMatrixTransform(g.Transform, true).(DrawPathList)
}
func (g Gradient) GetMatrixTransform() math2.MatrixTransform {
return g.Transform
func (g Gradient) ApplyMatrixTransform(transform math2.MatrixTransform, applyTranslation bool) Fillable {
if transform.IsIdentity() {
return g
}
g2 := g
if !applyTranslation {
panic("not supported")
}
g2.Transform = transform.Combine(g2.Transform)
return g2
}
func (g Gradient) ApplyColorTransform(transform math2.ColorTransform) Fillable {
@ -48,11 +48,15 @@ func (g Gradient) ApplyColorTransform(transform math2.ColorTransform) Fillable {
Color: transform.ApplyToColor(g.Color),
}
}
return &g2
return g2
}
func (g Gradient) Fill(shape Shape) DrawPathList {
return g.GetInterpolatedDrawPaths(settings.GlobalSettings.GradientOverlap, settings.GlobalSettings.GradientBlur, settings.GlobalSettings.GradientSlices).Fill(shape)
bb := Rectangle[float64]{}
if inverse := g.Transform.Inverse(); inverse != nil {
bb = shape.ApplyMatrixTransform(*inverse, true).BoundingBox()
}
return g.GetInterpolatedDrawPaths(settings.GlobalSettings.GradientOverlap, settings.GlobalSettings.GradientBlur, settings.GlobalSettings.GradientSlices, bb).Fill(shape)
}
type GradientItem struct {
@ -79,7 +83,7 @@ func InterpolateGradient(gradient Gradient, gradientSlices int) (result []Gradie
items := gradient.GetItems()
//TODO: spread modes
interpolationMode := gradient.GetInterpolationMode()
interpolationMode := gradient.InterpolationMode
first := items[0]
last := items[len(items)-1]

View file

@ -6,6 +6,80 @@ import (
"git.gammaspectra.live/WeebDataHoarder/swf2ass-go/types/math"
)
func interpolateLinearGradient(self Gradient, overlap, blur float64, gradientSlices int, bb Rectangle[float64]) DrawPathList {
//items is max size 8 to 15 depending on SWF version
height0 := GradientBoundsMin.Float64()
height1 := GradientBoundsMax.Float64()
switch self.SpreadMode {
case swfsubtypes.GradientSpreadPad:
height0 = min(height0, bb.TopLeft.Y)
height1 = max(height1, bb.BottomRight.Y)
}
topLeft0 := math.NewVector2(GradientBoundsMin.Float64(), height0)
topLeft1 := math.NewVector2(GradientBoundsMax.Float64(), height0)
bottomRight0 := math.NewVector2(GradientBoundsMin.Float64(), height1)
bottomRight1 := math.NewVector2(GradientBoundsMax.Float64(), height1)
//TODO: more spreadMode, generalize
vOverlap := math.NewVector2(overlap, 0).Divide(2)
items := InterpolateGradient(self, gradientSlices)
var paths DrawPathList
for _, item := range items {
if item.Start == 0 {
switch self.SpreadMode {
case swfsubtypes.GradientSpreadPad:
if bb.TopLeft.X < topLeft0.X {
paths = append(paths, DrawPathFill(
&FillStyleRecord{
Fill: item.Color,
Blur: blur,
},
Rectangle[float64]{
TopLeft: math.NewVector2(bb.TopLeft.X, height0),
BottomRight: math.NewVector2(topLeft0.X, height1).AddVector(vOverlap),
}.Draw(),
))
}
}
}
paths = append(paths, DrawPathFill(
&FillStyleRecord{
Fill: item.Color,
Blur: blur,
},
Rectangle[float64]{
TopLeft: math.LerpVector2(topLeft0, topLeft1, item.Start).SubVector(vOverlap),
BottomRight: math.LerpVector2(bottomRight0, bottomRight1, item.End).AddVector(vOverlap),
}.Draw(),
))
if item.End == 1 {
switch self.SpreadMode {
case swfsubtypes.GradientSpreadPad:
if bb.BottomRight.X > bottomRight1.X {
paths = append(paths, DrawPathFill(
&FillStyleRecord{
Fill: item.Color,
Blur: blur,
},
Rectangle[float64]{
TopLeft: math.NewVector2(topLeft1.X, height0),
BottomRight: math.NewVector2(bb.BottomRight.X, height1).AddVector(vOverlap),
}.Draw(),
))
}
}
}
}
return paths
}
func LinearGradientFromSWF(records []swfsubtypes.GRADRECORD, transform types.MATRIX, spreadMode swfsubtypes.GradientSpreadMode, interpolationMode swfsubtypes.GradientInterpolationMode) Gradient {
items := make([]GradientItem, 0, len(records))
for _, r := range records {
@ -15,31 +89,10 @@ func LinearGradientFromSWF(records []swfsubtypes.GRADRECORD, transform types.MAT
//TODO: interpolationMode, spreadMode
return Gradient{
Records: items,
//TODO: do we need to scale this to pixel world from twips?
Transform: math.MatrixTransformFromSWF(transform),
Records: items,
Transform: math.MatrixTransformFromSWF(transform, 1),
SpreadMode: spreadMode,
InterpolationMode: interpolationMode,
Interpolation: func(self Gradient, overlap, blur float64, gradientSlices int) DrawPathList {
//items is max size 8 to 15 depending on SWF version
size := GradientBounds.Width()
//TODO spreadMode
var paths DrawPathList
for _, item := range InterpolateGradient(self, gradientSlices) {
paths = append(paths, DrawPathFill(
&FillStyleRecord{
Fill: item.Color,
Blur: blur,
},
Rectangle[float64]{
TopLeft: math.NewVector2(GradientBounds.TopLeft.X+item.Start*size-overlap/2, GradientBounds.TopLeft.Y),
BottomRight: math.NewVector2(GradientBounds.TopLeft.X+item.End*size+overlap/2, GradientBounds.BottomRight.Y),
}.Draw(),
).ApplyMatrixTransform(self.Transform, true))
}
return paths
},
Interpolation: interpolateLinearGradient,
}
}

View file

@ -6,6 +6,36 @@ import (
"git.gammaspectra.live/WeebDataHoarder/swf2ass-go/types/math"
)
func interpolateRadialGradient(self Gradient, overlap, blur float64, gradientSlices int, bb Rectangle[float64]) DrawPathList {
//items is max size 8 to 15 depending on SWF version
size := GradientBounds.Width()
//TODO spreadMode
var paths DrawPathList
for _, item := range InterpolateGradient(self, gradientSlices) {
//Create concentric circles to cut out a shape
var shape Shape
radiusStart := (item.Start*size)/2 - overlap/4
radiusEnd := (item.End*size)/2 + overlap/4
start := NewCircle(math.NewVector2[float64](0, 0), radiusStart).Draw()
if radiusStart <= 0 {
start = nil
}
end := NewCircle(math.NewVector2[float64](0, 0), radiusEnd).Draw()
shape = append(shape, end...)
shape = append(shape, start.Reverse()...)
paths = append(paths, DrawPathFill(
&FillStyleRecord{
Fill: item.Color,
Blur: blur,
},
shape,
))
}
return paths
}
func RadialGradientFromSWF(records []swfsubtypes.GRADRECORD, transform types.MATRIX, spreadMode swfsubtypes.GradientSpreadMode, interpolationMode swfsubtypes.GradientInterpolationMode) Gradient {
items := make([]GradientItem, 0, len(records))
for _, r := range records {
@ -17,37 +47,9 @@ func RadialGradientFromSWF(records []swfsubtypes.GRADRECORD, transform types.MAT
return Gradient{
Records: items,
//TODO: do we need to scale this to pixel world from twips?
Transform: math.MatrixTransformFromSWF(transform),
Transform: math.MatrixTransformFromSWF(transform, 1),
SpreadMode: spreadMode,
InterpolationMode: interpolationMode,
Interpolation: func(self Gradient, overlap, blur float64, gradientSlices int) DrawPathList {
//items is max size 8 to 15 depending on SWF version
size := GradientBounds.Width()
//TODO spreadMode
var paths DrawPathList
for _, item := range InterpolateGradient(self, gradientSlices) {
//Create concentric circles to cut out a shape
var shape Shape
radiusStart := (item.Start*size)/2 - overlap/4
radiusEnd := (item.End*size)/2 + overlap/4
start := NewCircle(math.NewVector2[float64](0, 0), radiusStart).Draw()
if radiusStart <= 0 {
start = nil
}
end := NewCircle(math.NewVector2[float64](0, 0), radiusEnd).Draw()
shape = append(shape, end...)
shape = append(shape, start.Reverse()...)
paths = append(paths, DrawPathFill(
&FillStyleRecord{
Fill: item.Color,
Blur: blur,
},
shape,
))
}
return paths.ApplyMatrixTransform(self.Transform, true)
},
Interpolation: interpolateRadialGradient,
}
}

View file

@ -58,6 +58,20 @@ func (s Shape) Merge(o Shape) (r Shape) {
return r
}
func (s Shape) BoundingBox() Rectangle[float64] {
rect := Rectangle[float64]{}
if len(s) == 0 {
return rect
}
rect.TopLeft, rect.BottomRight = s[0].BoundingBox()
for _, r := range s[1:] {
tl, br := r.BoundingBox()
rect.TopLeft = rect.TopLeft.Min(tl)
rect.BottomRight = rect.BottomRight.Max(br)
}
return rect
}
// Flatten Converts all non-linear records into line segments and returns a new Shape
func (s Shape) Flatten() (r Shape) {
if s.IsFlat() {

View file

@ -16,6 +16,7 @@ type StyleRecord interface {
type Fillable interface {
Fill(shape Shape) DrawPathList
ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) Fillable
ApplyColorTransform(transform math.ColorTransform) Fillable
}
@ -60,14 +61,27 @@ func (r *FillStyleRecord) Flatten(s Shape) DrawPathList {
}
func (r *FillStyleRecord) ApplyMatrixTransform(transform math.MatrixTransform, applyTranslation bool) StyleRecord {
fill := r.Fill
if color, ok := fill.(math.Color); ok {
fill = color
} else if fillable, ok := r.Fill.(Fillable); ok {
fill = fillable.ApplyMatrixTransform(transform, applyTranslation)
} else {
panic("not supported")
}
if r.Border != nil {
return &FillStyleRecord{
Fill: r.Fill,
Fill: fill,
Border: r.Border.ApplyMatrixTransform(transform, applyTranslation).(*LineStyleRecord),
Blur: r.Blur, //TODO: scale blur?
}
}
return r
return &FillStyleRecord{
Fill: fill,
Border: nil,
Blur: r.Blur, //TODO: scale blur?
}
}
func (r *FillStyleRecord) ApplyColorTransform(transform math.ColorTransform) StyleRecord {

View file

@ -33,7 +33,7 @@ func (d *FontDefinition) ComposeTextSWF(entries []subtypes.GLYPHENTRY, height, y
e := d.Entries[g.Index]
t := math.TranslateTransform(math.NewVector2(xOffset, yOffset)).Multiply(math.ScaleTransform(math.NewVector2(height/d.Scale, height/d.Scale)))
for _, dp := range e.List.ApplyMatrixTransform(t, true) {
for _, dp := range e.List.ApplyMatrixTransform(t, true).(shapes.DrawPathList) {
if _, ok := dp.Style.(*shapes.FillStyleRecord); ok {
list = append(list, shapes.DrawPathFill(&shapes.FillStyleRecord{
Fill: c,
@ -142,7 +142,7 @@ func TextDefinitionFromSWF(collection shapes.ObjectCollection, characterId uint1
return &TextDefinition{
ObjectId: characterId,
Bounds: characterBounds,
ShapeList: r.ApplyMatrixTransform(math.MatrixTransformFromSWF(matrix), true),
ShapeList: r.ApplyMatrixTransform(math.MatrixTransformFromSWF(matrix, 1), true).(shapes.DrawPathList),
}
}
@ -150,9 +150,13 @@ func FontDefinitionFromSWF[T1 uint16 | uint32, T2 uint8 | uint16](fontId uint16,
styleList := shapes.StyleList{
//TODO: why is this needed????
FillStyles: []*shapes.FillStyleRecord{{}},
FillStyles: []*shapes.FillStyleRecord{{
Fill: math.Color{},
}},
//TODO: why is this needed????
LineStyles: []*shapes.LineStyleRecord{{}},
LineStyles: []*shapes.LineStyleRecord{{
Color: math.Color{},
}},
}
var entries []FontEntry