1 /* 2 * Copyright (C) 2007 Google (Evan Stade) 3 * 4 * This library is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU Lesser General Public 6 * License as published by the Free Software Foundation; either 7 * version 2.1 of the License, or (at your option) any later version. 8 * 9 * This library is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * Lesser General Public License for more details. 13 * 14 * You should have received a copy of the GNU Lesser General Public 15 * License along with this library; if not, write to the Free Software 16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 17 */ 18 19 #include "gdiplus_private.h" 20 21 GpStatus WINGDIPAPI GdipCloneCustomLineCap(GpCustomLineCap* from, 22 GpCustomLineCap** to) 23 { 24 TRACE("(%p, %p)\n", from, to); 25 26 if(!from || !to) 27 return InvalidParameter; 28 29 *to = heap_alloc_zero(sizeof(GpCustomLineCap)); 30 if(!*to) return OutOfMemory; 31 32 memcpy(*to, from, sizeof(GpCustomLineCap)); 33 34 (*to)->pathdata.Points = heap_alloc_zero(from->pathdata.Count * sizeof(PointF)); 35 (*to)->pathdata.Types = heap_alloc_zero(from->pathdata.Count); 36 37 if((!(*to)->pathdata.Types || !(*to)->pathdata.Points) && (*to)->pathdata.Count){ 38 heap_free((*to)->pathdata.Points); 39 heap_free((*to)->pathdata.Types); 40 heap_free(*to); 41 return OutOfMemory; 42 } 43 44 memcpy((*to)->pathdata.Points, from->pathdata.Points, from->pathdata.Count 45 * sizeof(PointF)); 46 memcpy((*to)->pathdata.Types, from->pathdata.Types, from->pathdata.Count); 47 48 TRACE("<-- %p\n", *to); 49 50 return Ok; 51 } 52 53 /* FIXME: Sometimes when fillPath is non-null and stroke path is null, the native 54 * version of this function returns NotImplemented. I cannot figure out why. */ 55 GpStatus WINGDIPAPI GdipCreateCustomLineCap(GpPath* fillPath, GpPath* strokePath, 56 GpLineCap baseCap, REAL baseInset, GpCustomLineCap **customCap) 57 { 58 GpPathData *pathdata; 59 60 TRACE("%p %p %d %f %p\n", fillPath, strokePath, baseCap, baseInset, customCap); 61 62 if(!customCap || !(fillPath || strokePath)) 63 return InvalidParameter; 64 65 *customCap = heap_alloc_zero(sizeof(GpCustomLineCap)); 66 if(!*customCap) return OutOfMemory; 67 68 (*customCap)->type = CustomLineCapTypeDefault; 69 if(strokePath){ 70 (*customCap)->fill = FALSE; 71 pathdata = &strokePath->pathdata; 72 } 73 else{ 74 (*customCap)->fill = TRUE; 75 pathdata = &fillPath->pathdata; 76 } 77 78 (*customCap)->pathdata.Points = heap_alloc_zero(pathdata->Count * sizeof(PointF)); 79 (*customCap)->pathdata.Types = heap_alloc_zero(pathdata->Count); 80 81 if((!(*customCap)->pathdata.Types || !(*customCap)->pathdata.Points) && 82 pathdata->Count){ 83 heap_free((*customCap)->pathdata.Points); 84 heap_free((*customCap)->pathdata.Types); 85 heap_free(*customCap); 86 return OutOfMemory; 87 } 88 89 memcpy((*customCap)->pathdata.Points, pathdata->Points, pathdata->Count 90 * sizeof(PointF)); 91 memcpy((*customCap)->pathdata.Types, pathdata->Types, pathdata->Count); 92 (*customCap)->pathdata.Count = pathdata->Count; 93 94 (*customCap)->inset = baseInset; 95 (*customCap)->cap = baseCap; 96 (*customCap)->join = LineJoinMiter; 97 (*customCap)->scale = 1.0; 98 99 TRACE("<-- %p\n", *customCap); 100 101 return Ok; 102 } 103 104 GpStatus WINGDIPAPI GdipDeleteCustomLineCap(GpCustomLineCap *customCap) 105 { 106 TRACE("(%p)\n", customCap); 107 108 if(!customCap) 109 return InvalidParameter; 110 111 heap_free(customCap->pathdata.Points); 112 heap_free(customCap->pathdata.Types); 113 heap_free(customCap); 114 115 return Ok; 116 } 117 118 GpStatus WINGDIPAPI GdipGetCustomLineCapStrokeJoin(GpCustomLineCap* customCap, 119 GpLineJoin* lineJoin) 120 { 121 TRACE("(%p, %p)\n", customCap, lineJoin); 122 123 if(!customCap || !lineJoin) 124 return InvalidParameter; 125 126 *lineJoin = customCap->join; 127 128 return Ok; 129 } 130 131 GpStatus WINGDIPAPI GdipGetCustomLineCapWidthScale(GpCustomLineCap* custom, 132 REAL* widthScale) 133 { 134 TRACE("(%p, %p)\n", custom, widthScale); 135 136 if(!custom || !widthScale) 137 return InvalidParameter; 138 139 *widthScale = custom->scale; 140 141 return Ok; 142 } 143 144 GpStatus WINGDIPAPI GdipSetCustomLineCapStrokeCaps(GpCustomLineCap* custom, 145 GpLineCap start, GpLineCap end) 146 { 147 static int calls; 148 149 TRACE("(%p,%u,%u)\n", custom, start, end); 150 151 if(!custom) 152 return InvalidParameter; 153 154 if(!(calls++)) 155 FIXME("not implemented\n"); 156 157 return NotImplemented; 158 } 159 160 GpStatus WINGDIPAPI GdipSetCustomLineCapBaseCap(GpCustomLineCap* custom, 161 GpLineCap base) 162 { 163 static int calls; 164 165 TRACE("(%p,%u)\n", custom, base); 166 167 if(!(calls++)) 168 FIXME("not implemented\n"); 169 170 return NotImplemented; 171 } 172 173 GpStatus WINGDIPAPI GdipGetCustomLineCapBaseInset(GpCustomLineCap* custom, 174 REAL* inset) 175 { 176 TRACE("(%p, %p)\n", custom, inset); 177 178 if(!custom || !inset) 179 return InvalidParameter; 180 181 *inset = custom->inset; 182 183 return Ok; 184 } 185 186 GpStatus WINGDIPAPI GdipSetCustomLineCapBaseInset(GpCustomLineCap* custom, 187 REAL inset) 188 { 189 static int calls; 190 191 TRACE("(%p,%0.2f)\n", custom, inset); 192 193 if(!(calls++)) 194 FIXME("not implemented\n"); 195 196 return NotImplemented; 197 } 198 199 /*FIXME: LineJoin completely ignored now */ 200 GpStatus WINGDIPAPI GdipSetCustomLineCapStrokeJoin(GpCustomLineCap* custom, 201 GpLineJoin join) 202 { 203 TRACE("(%p, %d)\n", custom, join); 204 205 if(!custom) 206 return InvalidParameter; 207 208 custom->join = join; 209 210 return Ok; 211 } 212 213 GpStatus WINGDIPAPI GdipSetCustomLineCapWidthScale(GpCustomLineCap* custom, REAL width) 214 { 215 TRACE("(%p,%0.2f)\n", custom, width); 216 217 if(!custom) 218 return InvalidParameter; 219 220 custom->scale = width; 221 222 return Ok; 223 } 224 225 GpStatus WINGDIPAPI GdipGetCustomLineCapBaseCap(GpCustomLineCap *customCap, GpLineCap *baseCap) 226 { 227 TRACE("(%p, %p)\n", customCap, baseCap); 228 229 if(!customCap || !baseCap) 230 return InvalidParameter; 231 232 *baseCap = customCap->cap; 233 234 return Ok; 235 } 236 237 GpStatus WINGDIPAPI GdipGetCustomLineCapType(GpCustomLineCap *customCap, CustomLineCapType *type) 238 { 239 TRACE("(%p, %p)\n", customCap, type); 240 241 if(!customCap || !type) 242 return InvalidParameter; 243 244 *type = customCap->type; 245 return Ok; 246 } 247 248 GpStatus WINGDIPAPI GdipCreateAdjustableArrowCap(REAL height, REAL width, BOOL fill, 249 GpAdjustableArrowCap **cap) 250 { 251 static int calls; 252 253 TRACE("(%0.2f,%0.2f,%i,%p)\n", height, width, fill, cap); 254 255 if(!(calls++)) 256 FIXME("not implemented\n"); 257 258 return NotImplemented; 259 } 260 261 GpStatus WINGDIPAPI GdipGetAdjustableArrowCapFillState(GpAdjustableArrowCap* cap, BOOL* fill) 262 { 263 static int calls; 264 265 TRACE("(%p,%p)\n", cap, fill); 266 267 if(!(calls++)) 268 FIXME("not implemented\n"); 269 270 return NotImplemented; 271 } 272 273 GpStatus WINGDIPAPI GdipGetAdjustableArrowCapHeight(GpAdjustableArrowCap* cap, REAL* height) 274 { 275 static int calls; 276 277 TRACE("(%p,%p)\n", cap, height); 278 279 if(!(calls++)) 280 FIXME("not implemented\n"); 281 282 return NotImplemented; 283 } 284 285 GpStatus WINGDIPAPI GdipGetAdjustableArrowCapMiddleInset(GpAdjustableArrowCap* cap, REAL* middle) 286 { 287 static int calls; 288 289 TRACE("(%p,%p)\n", cap, middle); 290 291 if(!(calls++)) 292 FIXME("not implemented\n"); 293 294 return NotImplemented; 295 } 296 297 GpStatus WINGDIPAPI GdipGetAdjustableArrowCapWidth(GpAdjustableArrowCap* cap, REAL* width) 298 { 299 static int calls; 300 301 TRACE("(%p,%p)\n", cap, width); 302 303 if(!(calls++)) 304 FIXME("not implemented\n"); 305 306 return NotImplemented; 307 } 308 309 GpStatus WINGDIPAPI GdipSetAdjustableArrowCapFillState(GpAdjustableArrowCap* cap, BOOL fill) 310 { 311 static int calls; 312 313 TRACE("(%p,%i)\n", cap, fill); 314 315 if(!(calls++)) 316 FIXME("not implemented\n"); 317 318 return NotImplemented; 319 } 320 321 GpStatus WINGDIPAPI GdipSetAdjustableArrowCapHeight(GpAdjustableArrowCap* cap, REAL height) 322 { 323 static int calls; 324 325 TRACE("(%p,%0.2f)\n", cap, height); 326 327 if(!(calls++)) 328 FIXME("not implemented\n"); 329 330 return NotImplemented; 331 } 332 333 GpStatus WINGDIPAPI GdipSetAdjustableArrowCapMiddleInset(GpAdjustableArrowCap* cap, REAL middle) 334 { 335 static int calls; 336 337 TRACE("(%p,%0.2f)\n", cap, middle); 338 339 if(!(calls++)) 340 FIXME("not implemented\n"); 341 342 return NotImplemented; 343 } 344 345 GpStatus WINGDIPAPI GdipSetAdjustableArrowCapWidth(GpAdjustableArrowCap* cap, REAL width) 346 { 347 static int calls; 348 349 TRACE("(%p,%0.2f)\n", cap, width); 350 351 if(!(calls++)) 352 FIXME("not implemented\n"); 353 354 return NotImplemented; 355 } 356