1544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin/**************************************************************************
2544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin *
3544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * Copyright 2009 VMware, Inc.  All Rights Reserved.
4544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin *
5544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * Permission is hereby granted, free of charge, to any person obtaining a
6544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * copy of this software and associated documentation files (the
7544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * "Software"), to deal in the Software without restriction, including
8544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * without limitation the rights to use, copy, modify, merge, publish,
9544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * distribute, sub license, and/or sell copies of the Software, and to
10544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * permit persons to whom the Software is furnished to do so, subject to
11544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * the following conditions:
12544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin *
13544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * The above copyright notice and this permission notice (including the
14544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * next paragraph) shall be included in all copies or substantial portions
15544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * of the Software.
16544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin *
17544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
20544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
21544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
22544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
23544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin *
25544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin **************************************************************************/
26544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
27544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#include "VG/openvg.h"
28544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
29544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#include "vg_context.h"
30d41e694cf78ada8c9258f96995115c9da8437894Brian Paul#include "handle.h"
31544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#include "path.h"
3275143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu#include "api.h"
33544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
34544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#include "pipe/p_context.h"
35544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
3675143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I WuVGPath vegaCreatePath(VGint pathFormat,
3775143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                      VGPathDatatype datatype,
3875143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                      VGfloat scale, VGfloat bias,
3975143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                      VGint segmentCapacityHint,
4075143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                      VGint coordCapacityHint,
4175143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                      VGbitfield capabilities)
42544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
43544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
44544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
45544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (pathFormat != VG_PATH_FORMAT_STANDARD) {
46544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_UNSUPPORTED_PATH_FORMAT_ERROR);
47544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return VG_INVALID_HANDLE;
48544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
49544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (datatype < VG_PATH_DATATYPE_S_8 ||
50544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       datatype > VG_PATH_DATATYPE_F) {
51544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
52544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return VG_INVALID_HANDLE;
53544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
54544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!scale) {
55544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
56544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return VG_INVALID_HANDLE;
57544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
58544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
59d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   return path_to_handle(path_create(datatype, scale, bias,
60d41e694cf78ada8c9258f96995115c9da8437894Brian Paul                                     segmentCapacityHint, coordCapacityHint,
61d41e694cf78ada8c9258f96995115c9da8437894Brian Paul                                     capabilities));
62544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
63544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
6475143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaClearPath(VGPath path, VGbitfield capabilities)
65544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
66544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
67544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
68544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
69544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
70544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
71544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
72544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
73544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
74d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
75544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_clear(p, capabilities);
76544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
77544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
7875143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaDestroyPath(VGPath p)
79544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
80544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *path = 0;
81544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
82544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
83544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (p == VG_INVALID_HANDLE) {
84544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
85544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
86544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
87544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
88d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   path = handle_to_path(p);
89544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_destroy(path);
90544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
91544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
9275143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaRemovePathCapabilities(VGPath path,
9375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                                VGbitfield capabilities)
94544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
95544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
96544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   VGbitfield current;
97544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p;
98544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
99544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
100544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
101544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
102544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
103544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
104d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
105544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   current = path_capabilities(p);
106544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_set_capabilities(p, (current &
107544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                             (~(capabilities & VG_PATH_CAPABILITY_ALL))));
108544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
109544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
11075143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I WuVGbitfield vegaGetPathCapabilities(VGPath path)
111544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
112544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
113544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
114544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
115544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
116544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
117544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return 0;
118544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
119d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
120544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   return path_capabilities(p);
121544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
122544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
12375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaAppendPath(VGPath dstPath, VGPath srcPath)
124544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
125544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
126544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *src, *dst;
127544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
128544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (dstPath == VG_INVALID_HANDLE || srcPath == VG_INVALID_HANDLE) {
129544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
130544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
131544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
132d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   src = handle_to_path(srcPath);
133d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   dst = handle_to_path(dstPath);
134544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
135544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(path_capabilities(src) & VG_PATH_CAPABILITY_APPEND_FROM) ||
136544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !(path_capabilities(dst) & VG_PATH_CAPABILITY_APPEND_TO)) {
137544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
138544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
139544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
140544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_append_path(dst, src);
141544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
142544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
14375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaAppendPathData(VGPath dstPath,
14475143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGint numSegments,
14575143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        const VGubyte * pathSegments,
14675143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        const void * pathData)
147544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
148544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
149544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
150544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   VGint i;
151544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
152544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (dstPath == VG_INVALID_HANDLE) {
153544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
154544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
155544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
156544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!pathSegments) {
157544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
158544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
159544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
160544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (numSegments <= 0) {
161544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
162544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
163544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
164544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   for (i = 0; i < numSegments; ++i) {
165bf63b9d7a942bfbeef0b2b765bfc346c93de6fb7Vinson Lee      if (pathSegments[i] > VG_LCWARC_TO_REL) {
166544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin         vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
167544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin         return;
168544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      }
169544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
170544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
171d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(dstPath);
172544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
17399c67f27d35a4bbbbefada8117d5972c7583cf42Brian Paul   if (!p || !is_aligned_to(p, path_datatype_size(p))) {
174544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
175544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
176544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
177544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
178544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(path_capabilities(p)&VG_PATH_CAPABILITY_APPEND_TO)) {
179544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
180544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
181544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
182544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
183544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_append_data(p, numSegments, pathSegments, pathData);
184544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
185544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
18675143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaModifyPathCoords(VGPath dstPath,
18775143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                          VGint startIndex,
18875143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                          VGint numSegments,
18975143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                          const void * pathData)
190544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
191544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
192544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
193544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
194544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (dstPath == VG_INVALID_HANDLE) {
195544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
196544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
197544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
198544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (startIndex < 0 || numSegments <= 0) {
199544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
200544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
201544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
202544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
203d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(dstPath);
204544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
205544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!pathData || !is_aligned_to(pathData, path_datatype_size(p))) {
206544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
207544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
208544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
209544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
210544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (startIndex + numSegments > path_num_segments(p)) {
211544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
212544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
213544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
214544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(path_capabilities(p)&VG_PATH_CAPABILITY_MODIFY)) {
215544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
216544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
217544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
218544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_modify_coords(p, startIndex, numSegments, pathData);
219544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
220544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
22175143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaTransformPath(VGPath dstPath, VGPath srcPath)
222544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
223544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
224544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *src = 0, *dst = 0;
225544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
226544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (dstPath == VG_INVALID_HANDLE || srcPath == VG_INVALID_HANDLE) {
227544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
228544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
229544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
230d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   src = handle_to_path(srcPath);
231d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   dst = handle_to_path(dstPath);
232544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
233544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(path_capabilities(src) & VG_PATH_CAPABILITY_TRANSFORM_FROM) ||
234544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !(path_capabilities(dst) & VG_PATH_CAPABILITY_TRANSFORM_TO)) {
235544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
236544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
237544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
238544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_transform(dst, src);
239544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
240544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
24175143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I WuVGboolean vegaInterpolatePath(VGPath dstPath,
24275143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                              VGPath startPath,
24375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                              VGPath endPath,
24475143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                              VGfloat amount)
245544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
246544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
247544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *start = 0, *dst = 0, *end = 0;
248544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
249544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (dstPath == VG_INVALID_HANDLE ||
250544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       startPath == VG_INVALID_HANDLE ||
251544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       endPath == VG_INVALID_HANDLE) {
252544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
253544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return VG_FALSE;
254544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
255d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   dst = handle_to_path(dstPath);
256d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   start = handle_to_path(startPath);
257d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   end = handle_to_path(endPath);
258544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
259544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(path_capabilities(dst) & VG_PATH_CAPABILITY_INTERPOLATE_TO) ||
260544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !(path_capabilities(start) & VG_PATH_CAPABILITY_INTERPOLATE_FROM) ||
261544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !(path_capabilities(end) & VG_PATH_CAPABILITY_INTERPOLATE_FROM)) {
262544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
263544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return VG_FALSE;
264544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
265544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
266544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   return path_interpolate(dst,
267544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                           start, end, amount);
268544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
269544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
27075143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I WuVGfloat vegaPathLength(VGPath path,
27175143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                       VGint startSegment,
27275143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                       VGint numSegments)
273544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
274544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
275544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
276544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
277544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
278544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
279544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return -1;
280544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
281544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (startSegment < 0) {
282544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
283544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return -1;
284544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
285544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (numSegments <= 0) {
286544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
287544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return -1;
288544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
289d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
290544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
291544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(path_capabilities(p) & VG_PATH_CAPABILITY_PATH_LENGTH)) {
292544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
293544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return -1;
294544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
295544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (startSegment + numSegments > path_num_segments(p)) {
296544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
297544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return -1;
298544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
299544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
300544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   return path_length(p, startSegment, numSegments);
301544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
302544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
30375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaPointAlongPath(VGPath path,
30475143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGint startSegment,
30575143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGint numSegments,
30675143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGfloat distance,
30775143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGfloat * x, VGfloat * y,
30875143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGfloat * tangentX,
30975143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                        VGfloat * tangentY)
310544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
311544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
312544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
313544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   VGbitfield caps;
314544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
315544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
316544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
317544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
318544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
319544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (startSegment < 0) {
320544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
321544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
322544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
323544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (numSegments <= 0) {
324544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
325544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
326544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
327544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
328544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!is_aligned(x) || !is_aligned(y) ||
329544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !is_aligned(tangentX) || !is_aligned(tangentY)) {
330544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
331544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
332544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
333544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
334d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
335544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
336544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   caps = path_capabilities(p);
337544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(caps & VG_PATH_CAPABILITY_POINT_ALONG_PATH) ||
338544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !(caps & VG_PATH_CAPABILITY_TANGENT_ALONG_PATH)) {
339544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
340544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
341544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
342544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
343544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (startSegment + numSegments > path_num_segments(p)) {
344544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
345544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
346544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
347544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
348544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   {
349544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      VGfloat point[2], normal[2];
350544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      path_point(p, startSegment, numSegments, distance,
351544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                 point, normal);
352544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      if (x)
353544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin         *x = point[0];
354544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      if (y)
355544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin         *y = point[1];
356544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      if (tangentX)
357544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin         *tangentX = -normal[1];
358544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      if (tangentY)
359544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin         *tangentY = normal[0];
360544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
361544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
362544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
36375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaPathBounds(VGPath path,
36475143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                    VGfloat * minX,
36575143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                    VGfloat * minY,
36675143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                    VGfloat * width,
36775143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                    VGfloat * height)
368544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
369544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
370544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
371544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   VGbitfield caps;
372544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
373544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
374544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
375544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
376544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
377544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
378544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!minX || !minY || !width || !height) {
379544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
380544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
381544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
382544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
383544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!is_aligned(minX) || !is_aligned(minY) ||
384544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !is_aligned(width) || !is_aligned(height)) {
385544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
386544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
387544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
388544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
389d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
390544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
391544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   caps = path_capabilities(p);
392544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(caps & VG_PATH_CAPABILITY_PATH_BOUNDS)) {
393544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
394544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
395544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
396544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
397544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_bounding_rect(p, minX, minY, width, height);
398544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
399544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
40075143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaPathTransformedBounds(VGPath path,
40175143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                               VGfloat * minX,
40275143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                               VGfloat * minY,
40375143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                               VGfloat * width,
40475143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wu                               VGfloat * height)
405544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
406544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
407544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct path *p = 0;
408544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   VGbitfield caps;
409544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
410544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
411544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
412544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
413544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
414544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
415544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!minX || !minY || !width || !height) {
416544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
417544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
418544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
419544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
420544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!is_aligned(minX) || !is_aligned(minY) ||
421544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin       !is_aligned(width) || !is_aligned(height)) {
422544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
423544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
424544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
425544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
426d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   p = handle_to_path(path);
427544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
428544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   caps = path_capabilities(p);
429544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(caps & VG_PATH_CAPABILITY_PATH_TRANSFORMED_BOUNDS)) {
430544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_PATH_CAPABILITY_ERROR);
431544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
432544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
433544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
434544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#if 0
435544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   /* faster, but seems to have precision problems... */
436544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   path_bounding_rect(p, minX, minY, width, height);
437544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (*width > 0 && *height > 0) {
438544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      VGfloat pts[] = {*minX,          *minY,
439544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                       *minX + *width, *minY,
440544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                       *minX + *width, *minY + *height,
441544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                       *minX,          *minY + *height};
442544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      struct matrix *matrix = &ctx->state.vg.path_user_to_surface_matrix;
443544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      VGfloat maxX, maxY;
444544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      matrix_map_point(matrix, pts[0], pts[1], pts + 0, pts + 1);
445544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      matrix_map_point(matrix, pts[2], pts[3], pts + 2, pts + 3);
446544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      matrix_map_point(matrix, pts[4], pts[5], pts + 4, pts + 5);
447544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      matrix_map_point(matrix, pts[6], pts[7], pts + 6, pts + 7);
448544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      *minX = MIN2(pts[0], MIN2(pts[2], MIN2(pts[4], pts[6])));
449544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      *minY = MIN2(pts[1], MIN2(pts[3], MIN2(pts[5], pts[7])));
450544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      maxX = MAX2(pts[0], MAX2(pts[2], MAX2(pts[4], pts[6])));
451544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      maxY = MAX2(pts[1], MAX2(pts[3], MAX2(pts[5], pts[7])));
452544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      *width  = maxX - *minX;
453544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      *height = maxY - *minY;
454544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
455544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#else
456544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   {
457544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      struct path *dst = path_create(VG_PATH_DATATYPE_F, 1.0, 0,
458544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin                                     0, 0, VG_PATH_CAPABILITY_ALL);
459544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      path_transform(dst, p);
460544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      path_bounding_rect(dst, minX, minY, width, height);
461544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      path_destroy(dst);
462544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
463544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin#endif
464544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
465544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
466544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
46775143ef05576ee9f25ee176bc28c3c4d03705bf5Chia-I Wuvoid vegaDrawPath(VGPath path, VGbitfield paintModes)
468544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin{
469544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   struct vg_context *ctx = vg_current_context();
470d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   struct path *p = handle_to_path(path);
471544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
472544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (path == VG_INVALID_HANDLE) {
473544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_BAD_HANDLE_ERROR);
474544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
475544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
476544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
477544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   if (!(paintModes & (VG_STROKE_PATH | VG_FILL_PATH))) {
478544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      vg_set_error(ctx, VG_ILLEGAL_ARGUMENT_ERROR);
479544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
480544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin   }
481544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
482d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   if (path_is_empty(p))
483544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin      return;
484d41e694cf78ada8c9258f96995115c9da8437894Brian Paul   path_render(p, paintModes,
485165cb19abc4279839b0f5f53eb2feac60c2f415eChia-I Wu         &ctx->state.vg.path_user_to_surface_matrix);
486544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin}
487544dd4b11f7be76bb00fe29a60eaf2772dcc69caZack Rusin
488