xref: /aosp_15_r20/external/skia/include/core/SkVertices.h (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
1 /*
2  * Copyright 2017 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef SkVertices_DEFINED
9 #define SkVertices_DEFINED
10 
11 #include "include/core/SkColor.h"
12 #include "include/core/SkPoint.h"
13 #include "include/core/SkRect.h"
14 #include "include/core/SkRefCnt.h"
15 #include "include/private/base/SkAPI.h"
16 
17 #include <cstddef>
18 #include <cstdint>
19 #include <memory>
20 
21 class SkVerticesPriv;
22 
23 /**
24  * An immutable set of vertex data that can be used with SkCanvas::drawVertices.
25  */
26 class SK_API SkVertices : public SkNVRefCnt<SkVertices> {
27     struct Desc;
28     struct Sizes;
29 public:
30     enum VertexMode {
31         kTriangles_VertexMode,
32         kTriangleStrip_VertexMode,
33         kTriangleFan_VertexMode,
34 
35         kLast_VertexMode = kTriangleFan_VertexMode,
36     };
37 
38     /**
39      *  Create a vertices by copying the specified arrays. texs, colors may be nullptr,
40      *  and indices is ignored if indexCount == 0.
41      */
42     static sk_sp<SkVertices> MakeCopy(VertexMode mode, int vertexCount,
43                                       const SkPoint positions[],
44                                       const SkPoint texs[],
45                                       const SkColor colors[],
46                                       int indexCount,
47                                       const uint16_t indices[]);
48 
MakeCopy(VertexMode mode,int vertexCount,const SkPoint positions[],const SkPoint texs[],const SkColor colors[])49     static sk_sp<SkVertices> MakeCopy(VertexMode mode, int vertexCount,
50                                       const SkPoint positions[],
51                                       const SkPoint texs[],
52                                       const SkColor colors[]) {
53         return MakeCopy(mode,
54                         vertexCount,
55                         positions,
56                         texs,
57                         colors,
58                         0,
59                         nullptr);
60     }
61 
62     enum BuilderFlags {
63         kHasTexCoords_BuilderFlag   = 1 << 0,
64         kHasColors_BuilderFlag      = 1 << 1,
65     };
66     class SK_API Builder {
67     public:
68         Builder(VertexMode mode, int vertexCount, int indexCount, uint32_t flags);
69 
isValid()70         bool isValid() const { return fVertices != nullptr; }
71 
72         SkPoint* positions();
73         uint16_t* indices();        // returns null if there are no indices
74 
75         // If we have custom attributes, these will always be null
76         SkPoint* texCoords();       // returns null if there are no texCoords
77         SkColor* colors();          // returns null if there are no colors
78 
79         // Detach the built vertices object. After the first call, this will always return null.
80         sk_sp<SkVertices> detach();
81 
82     private:
83         Builder(const Desc&);
84 
85         void init(const Desc&);
86 
87         // holds a partially complete object. only completed in detach()
88         sk_sp<SkVertices> fVertices;
89         // Extra storage for intermediate vertices in the case where the client specifies indexed
90         // triangle fans. These get converted to indexed triangles when the Builder is finalized.
91         std::unique_ptr<uint8_t[]> fIntermediateFanIndices;
92 
93         friend class SkVertices;
94         friend class SkVerticesPriv;
95     };
96 
uniqueID()97     uint32_t uniqueID() const { return fUniqueID; }
bounds()98     const SkRect& bounds() const { return fBounds; }
99 
100     // returns approximate byte size of the vertices object
101     size_t approximateSize() const;
102 
103     // Provides access to functions that aren't part of the public API.
104     SkVerticesPriv priv();
105     const SkVerticesPriv priv() const;  // NOLINT(readability-const-return-type)
106 
107 private:
SkVertices()108     SkVertices() {}
109 
110     friend class SkVerticesPriv;
111 
112     // these are needed since we've manually sized our allocation (see Builder::init)
113     friend class SkNVRefCnt<SkVertices>;
114     void operator delete(void* p);
115 
116     Sizes getSizes() const;
117 
118     // we store this first, to pair with the refcnt in our base-class, so we don't have an
119     // unnecessary pad between it and the (possibly 8-byte aligned) ptrs.
120     uint32_t fUniqueID;
121 
122     // these point inside our allocation, so none of these can be "freed"
123     SkPoint*     fPositions;        // [vertexCount]
124     uint16_t*    fIndices;          // [indexCount] or null
125     SkPoint*     fTexs;             // [vertexCount] or null
126     SkColor*     fColors;           // [vertexCount] or null
127 
128     SkRect  fBounds;    // computed to be the union of the fPositions[]
129     int     fVertexCount;
130     int     fIndexCount;
131 
132     VertexMode fMode;
133     // below here is where the actual array data is stored.
134 };
135 
136 #endif
137