From a7e85a37e4f15eb6e61fb6c758c0f665a48c128f Mon Sep 17 00:00:00 2001 From: aoyako Date: Sat, 13 Apr 2024 20:04:36 +0900 Subject: [PATCH] use pointers in transformers --- image.go | 4 ++-- image_test.go | 37 ++++++++++++++++++++++++++++++++++--- path.go | 26 +++++++++++++------------- shape.go | 49 +++++++++++++++++++++++-------------------------- transform.go | 10 +++++----- 5 files changed, 77 insertions(+), 49 deletions(-) diff --git a/image.go b/image.go index 8f17b64..df0ee02 100644 --- a/image.go +++ b/image.go @@ -51,7 +51,7 @@ func ReadImage(r io.Reader) (*Image, error) { if err != nil { return nil, fmt.Errorf("reading path [%d]: %w", i, err) } - img.pathes = append(img.pathes, p) + img.pathes = append(img.pathes, &p) } var shapeCount uint8 @@ -65,7 +65,7 @@ func ReadImage(r io.Reader) (*Image, error) { if err != nil { return nil, fmt.Errorf("reading shape [%d]: %w", i, err) } - img.shapes = append(img.shapes, s) + img.shapes = append(img.shapes, &s) } return img, nil diff --git a/image_test.go b/image_test.go index 324a524..7c8776b 100644 --- a/image_test.go +++ b/image_test.go @@ -24,6 +24,10 @@ func asserPointsAreEqual(t *testing.T, e, a Point, msg any) { assert.InDelta(t, e.Y, a.Y, 0.1, msg) } +func getPointer(x uint8) *uint8 { + return &x +} + func TestRead(t *testing.T) { testdata := []struct { file string @@ -148,7 +152,7 @@ func TestRead(t *testing.T) { &Curve{PointIn: Point{44, 46}, Point: Point{40, 46}, PointOut: Point{48, 46}}, &Curve{PointIn: Point{55, 45}, Point: Point{54, 46}, PointOut: Point{56, 44}}, &Curve{PointIn: Point{64, 42}, Point: Point{64, 45}, PointOut: Point{64, 40}}, - &Curve{PointIn: Point{61, 39}, Point: Point{59.9, 39.9}, PointOut: Point{61, 39}}, + &Curve{PointIn: Point{61, 39}, Point: Point{60, 40}, PointOut: Point{61, 39}}, &Curve{PointIn: Point{62, 34}, Point: Point{62, 37}, PointOut: Point{62, 28}}, &Curve{PointIn: Point{50, 22}, Point: Point{58, 26}, PointOut: Point{50, 22}}, }, @@ -164,6 +168,11 @@ func TestRead(t *testing.T) { }, }, }, + shapes: []*Shape{ + {Hinting: false, styleID: getPointer(0), pathIDs: []uint8{0}, Transforms: nil}, + {Hinting: false, styleID: getPointer(1), pathIDs: []uint8{3, 4, 5}, + Transforms: []Transformer{&TransformerStroke{Width: 4, LineJoin: MiterJoin, LineCap: ButtCap, MiterLimit: 4}}}, + }, }, }, } @@ -208,7 +217,7 @@ func TestRead(t *testing.T) { // Pathes aPathes := img.GetPathes() ePathes := tc.image.pathes - // assert.Len(t, aPathes, len(ePathes)) + assert.Len(t, aPathes, 10) for i := range len(aPathes[:2]) { assert.Equal(t, reflect.TypeOf(aPathes[i]), reflect.TypeOf(ePathes[i]), i) @@ -238,6 +247,28 @@ func TestRead(t *testing.T) { } } } - } + aShapes := img.GetShapes() + eShapes := tc.image.shapes + assert.Len(t, aShapes, 14) + for i := range len(aShapes[:2]) { + assert.Equal(t, reflect.TypeOf(aShapes[i]), reflect.TypeOf(aShapes[i]), i) + + assert.Equal(t, aShapes[i].Hinting, eShapes[i].Hinting, i) + assert.True(t, isNilOrObject(aShapes[i].styleID, eShapes[i].styleID), i) + if aShapes[i].styleID != nil { + assert.Equal(t, *aShapes[i].styleID, *eShapes[i].styleID, i) + } + assert.Equal(t, aShapes[i].pathIDs, eShapes[i].pathIDs, i) + + assert.True(t, isNilOrObject(aShapes[i].Transforms, eShapes[i].Transforms), i) + + assert.Len(t, aShapes[i].Transforms, len(eShapes[i].Transforms), i) + for tID := range len(eShapes[i].Transforms) { + aTrans := aShapes[i].Transforms[tID] + eTrans := eShapes[i].Transforms[tID] + assert.True(t, reflect.DeepEqual(aTrans, eTrans)) + } + } + } } diff --git a/path.go b/path.go index b2a1811..bd95107 100644 --- a/path.go +++ b/path.go @@ -85,12 +85,12 @@ func splitCommandTypes(rawTypes []uint8, count uint8) []pathCommandType { return pct } -func readPath(r io.Reader) (*Path, error) { - path := &Path{} +func readPath(r io.Reader) (Path, error) { + var path Path var flag pathFlag err := binary.Read(r, binary.LittleEndian, &flag) if err != nil { - return nil, fmt.Errorf("reading flags: %w", err) + return path, fmt.Errorf("reading flags: %w", err) } path.isClosed = flag&pathFlagClosed != 0 @@ -99,14 +99,14 @@ func readPath(r io.Reader) (*Path, error) { var count uint8 err := binary.Read(r, binary.LittleEndian, &count) if err != nil { - return nil, fmt.Errorf("reading count for path no curves: %w", err) + return path, fmt.Errorf("reading count for path no curves: %w", err) } var points []PathElement for i := byte(0); i < count; i++ { p, err := readPoint(r) if err != nil { - return nil, fmt.Errorf("reading point: %w", err) + return path, fmt.Errorf("reading point: %w", err) } points = append(points, p) } @@ -115,7 +115,7 @@ func readPath(r io.Reader) (*Path, error) { var count uint8 err := binary.Read(r, binary.LittleEndian, &count) if err != nil { - return nil, fmt.Errorf("reading count for path with commands: %w", err) + return path, fmt.Errorf("reading count for path with commands: %w", err) } // Each command is 2 bits, aligned in a byte @@ -123,7 +123,7 @@ func readPath(r io.Reader) (*Path, error) { pathRawCommandTypes := make([]uint8, bytesForCommandTypes) err = binary.Read(r, binary.LittleEndian, &pathRawCommandTypes) if err != nil { - return nil, fmt.Errorf("reading commands: %w", err) + return path, fmt.Errorf("reading commands: %w", err) } pathCommandTypes := splitCommandTypes(pathRawCommandTypes, count) @@ -135,25 +135,25 @@ func readPath(r io.Reader) (*Path, error) { case pathCommandHLine: c, err := readFloatCoord(r) if err != nil { - return nil, fmt.Errorf("reading hline coord: %w", err) + return path, fmt.Errorf("reading hline coord: %w", err) } line = &HLine{c} case pathCommandVLine: c, err := readFloatCoord(r) if err != nil { - return nil, fmt.Errorf("reading vline coord: %w", err) + return path, fmt.Errorf("reading vline coord: %w", err) } line = &VLine{c} case pathCommandLine: p, err := readPoint(r) if err != nil { - return nil, fmt.Errorf("reading point: %w", err) + return path, fmt.Errorf("reading point: %w", err) } line = &p case pathCommandCurve: c, err := readCurve(r) if err != nil { - return nil, fmt.Errorf("reading curve: %w", err) + return path, fmt.Errorf("reading curve: %w", err) } line = &c } @@ -165,13 +165,13 @@ func readPath(r io.Reader) (*Path, error) { var count uint8 err := binary.Read(r, binary.LittleEndian, &count) if err != nil { - return nil, fmt.Errorf("reading count for curves: %w", err) + return path, fmt.Errorf("reading count for curves: %w", err) } var points []PathElement for i := byte(0); i < count; i++ { c, err := readCurve(r) if err != nil { - return nil, fmt.Errorf("reading curve: %w", err) + return path, fmt.Errorf("reading curve: %w", err) } points = append(points, &c) } diff --git a/shape.go b/shape.go index 4faa527..910c313 100644 --- a/shape.go +++ b/shape.go @@ -24,90 +24,87 @@ const ( ) type Shape struct { - Hinting bool - styleID *uint8 - pathIDs []uint8 - // Transform *utils.Transformable - // Translate *utils.Translation - // LodScale *utils.LodScale + Hinting bool + styleID *uint8 + pathIDs []uint8 Transforms []Transformer } -func readShape(r io.Reader) (*Shape, error) { - s := &Shape{} +func readShape(r io.Reader) (Shape, error) { + var shape Shape var stype shapeType err := binary.Read(r, binary.LittleEndian, &stype) if err != nil { - return nil, fmt.Errorf("reading type: %w", err) + return shape, fmt.Errorf("reading type: %w", err) } if stype == shapePathSource { var styleID uint8 err := binary.Read(r, binary.LittleEndian, &styleID) if err != nil { - return nil, fmt.Errorf("reading style id: %w", err) + return shape, fmt.Errorf("reading style id: %w", err) } - s.styleID = &styleID + shape.styleID = &styleID var pathCount uint8 err = binary.Read(r, binary.LittleEndian, &pathCount) if err != nil { - return nil, fmt.Errorf("reading path count: %w", err) + return shape, fmt.Errorf("reading path count: %w", err) } for i := byte(0); i < pathCount; i++ { var pathID uint8 err := binary.Read(r, binary.LittleEndian, &pathID) if err != nil { - return nil, fmt.Errorf("reading path [%d] id: %w", i, err) + return shape, fmt.Errorf("reading path [%d] id: %w", i, err) } - s.pathIDs = append(s.pathIDs, pathID) + shape.pathIDs = append(shape.pathIDs, pathID) } var flags shapeFlag err = binary.Read(r, binary.LittleEndian, &flags) if err != nil { - return nil, fmt.Errorf("reading flags: %w", err) + return shape, fmt.Errorf("reading flags: %w", err) } if flags&shapeFlagTransform != 0 { t, err := readAffine(r) if err != nil { - return nil, fmt.Errorf("reading affine transformer: %w", err) + return shape, fmt.Errorf("reading affine transformer: %w", err) } - s.Transforms = append(s.Transforms, t) + shape.Transforms = append(shape.Transforms, &t) } if flags&shapeFlagTranslation != 0 { t, err := readTranslation(r) if err != nil { - return nil, fmt.Errorf("reading translation %w", err) + return shape, fmt.Errorf("reading translation %w", err) } - s.Transforms = append(s.Transforms, t) + shape.Transforms = append(shape.Transforms, &t) } if flags&shapeFlagLodScale != 0 { t, err := readLodScale(r) if err != nil { - return nil, fmt.Errorf("reading lod scale: %w", err) + return shape, fmt.Errorf("reading lod scale: %w", err) } - s.Transforms = append(s.Transforms, t) + shape.Transforms = append(shape.Transforms, &t) } if flags&shapeFlagHasTransformers != 0 { var count uint8 err := binary.Read(r, binary.LittleEndian, &count) if err != nil { - return nil, fmt.Errorf("reading transformers count: %w", err) + return shape, fmt.Errorf("reading transformers count: %w", err) } for i := range count { t, err := readTransformer(r) if err != nil { - return nil, fmt.Errorf("reading transformer [%d]: %w", i, err) + return shape, fmt.Errorf("reading transformer [%d]: %w", i, err) } - s.Transforms = append(s.Transforms, t) + shape.Transforms = append(shape.Transforms, t) } } if flags&shapeFlagHinting != 0 { - s.Hinting = true + shape.Hinting = true } } - return s, nil + return shape, nil } diff --git a/transform.go b/transform.go index c8df995..e715b9e 100644 --- a/transform.go +++ b/transform.go @@ -39,7 +39,7 @@ const ( ) // TransformerTranslation | TransformerLodScale | TransformerAffine | -// TransformerPerspective | TransformerContour | TransformerStroke. +// TransformerPerspective | TransformerContour | TransformerStroke type Transformer any type TransformerTranslation struct { @@ -158,12 +158,12 @@ func readTransformer(r io.Reader) (Transformer, error) { return nil, fmt.Errorf("reading affine transformer: %w", err) } - return t, nil + return &t, nil case transformerTypeContour: if t, err := readCountour(r); err != nil { return nil, fmt.Errorf("reading countour: %w", err) } else { - return t, nil + return &t, nil } case transformerTypePerspective: t, err := readTransformerPerspective(r) @@ -171,14 +171,14 @@ func readTransformer(r io.Reader) (Transformer, error) { return nil, fmt.Errorf("reading perspective transformer: %w", err) } - return t, nil + return &t, nil case transformerTypeStroke: t, err := readTransformerStroke(r) if err != nil { return t, fmt.Errorf("reaiding stroke transformer: %w", err) } - return t, nil + return &t, nil } return nil, fmt.Errorf("unknown transformer: %d", ttype)