1 module skia.SKColorSpaceStructs; 2 3 import skia.Definitions; 4 import skia.SKObject; 5 import skia.SkiaApi; 6 import skia.SKData; 7 import skia.SKMatrix44; 8 import skia.Exceptions; 9 10 import std.range; 11 12 enum SKColorSpaceRenderTargetGamma 13 { 14 Linear = 0, 15 Srgb = 1, 16 } 17 alias ToColorSpaceTransferFn = SkiaExtensions.ToColorSpaceTransferFn; 18 19 20 enum SKColorSpaceGamut 21 { 22 AdobeRgb = 1, 23 Dcip3D65 = 2, 24 Rec2020 = 3, 25 Srgb = 0, 26 } 27 28 29 alias ToColorSpaceXyz = SkiaExtensions.ToColorSpaceXyz; 30 31 32 33 enum SKColorSpaceType 34 { 35 Cmyk = 1, 36 Gray = 2, 37 Rgb = 0, 38 } 39 40 enum SKNamedGamma 41 { 42 Linear = 0, 43 Srgb = 1, 44 TwoDotTwoCurve = 2, 45 NonStandard = 3, 46 } 47 48 class SkiaExtensions 49 { 50 51 // static SKColorSpaceTransferFn ToColorSpaceTransferFn (this SKColorSpaceRenderTargetGamma gamma) 52 static SKColorSpaceTransferFn ToColorSpaceTransferFn (SKColorSpaceRenderTargetGamma gamma) 53 { 54 switch(gamma) 55 { 56 case SKColorSpaceRenderTargetGamma.Linear: 57 return SKColorSpaceTransferFn.Linear; 58 case SKColorSpaceRenderTargetGamma.Srgb: 59 return SKColorSpaceTransferFn.Srgb; 60 default: 61 throw new ArgumentOutOfRangeException (gamma.stringof); 62 } 63 } 64 65 66 // static SKColorSpaceTransferFn ToColorSpaceTransferFn (this SKNamedGamma gamma) 67 static SKColorSpaceTransferFn ToColorSpaceTransferFn (SKNamedGamma gamma) 68 { 69 switch(gamma) 70 { 71 case SKNamedGamma.Linear: 72 return SKColorSpaceTransferFn.Linear; 73 case SKNamedGamma.Srgb: 74 return SKColorSpaceTransferFn.Srgb; 75 case SKNamedGamma.TwoDotTwoCurve: 76 return SKColorSpaceTransferFn.TwoDotTwo; 77 case SKNamedGamma.NonStandard: 78 return SKColorSpaceTransferFn.Empty; 79 default: 80 throw new ArgumentOutOfRangeException (gamma.stringof); 81 } 82 } 83 84 85 // static SKColorSpaceXyz ToColorSpaceXyz (this SKColorSpaceGamut gamut) 86 static SKColorSpaceXyz ToColorSpaceXyz (SKColorSpaceGamut gamut) 87 { 88 switch(gamut) 89 { 90 case SKColorSpaceGamut.AdobeRgb: 91 return SKColorSpaceXyz.AdobeRgb; 92 case SKColorSpaceGamut.Dcip3D65: 93 return SKColorSpaceXyz.Dcip3; 94 case SKColorSpaceGamut.Rec2020: 95 return SKColorSpaceXyz.Rec2020; 96 case SKColorSpaceGamut.Srgb: 97 return SKColorSpaceXyz.Srgb; 98 default: 99 throw new ArgumentOutOfRangeException (gamut.stringof); 100 } 101 } 102 103 104 // static SKColorSpaceXyz ToColorSpaceXyz (this SKMatrix44 matrix) 105 static SKColorSpaceXyz ToColorSpaceXyz (SKMatrix44 matrix) 106 { 107 if (matrix is null) 108 throw new ArgumentNullException (matrix.stringof); 109 110 auto values = matrix.ToRowMajor (); 111 return SKColorSpaceXyz ( 112 values[0], values[1], values[2], 113 values[4], values[5], values[6], 114 values[8], values[9], values[10]); 115 } 116 } 117 118 // struct SKColorSpacePrimaries 119 // { 120 121 122 // } 123 124 // struct SKColorSpaceTransferFn 125 // { 126 // static SKColorSpaceTransferFn Srgb() 127 // { 128 // SKColorSpaceTransferFn fn; 129 // SkiaApi.sk_colorspace_transfer_fn_named_srgb (&fn); 130 // return fn; 131 // } 132 133 // static SKColorSpaceTransferFn TwoDotTwo() 134 // { 135 // SKColorSpaceTransferFn fn; 136 // SkiaApi.sk_colorspace_transfer_fn_named_2dot2 (&fn); 137 // return fn; 138 // } 139 140 // static SKColorSpaceTransferFn Linear() 141 // { 142 // SKColorSpaceTransferFn fn; 143 // SkiaApi.sk_colorspace_transfer_fn_named_linear (&fn); 144 // return fn; 145 // } 146 147 // static SKColorSpaceTransferFn Rec2020() 148 // { 149 // SKColorSpaceTransferFn fn; 150 // SkiaApi.sk_colorspace_transfer_fn_named_rec2020 (&fn); 151 // return fn; 152 // } 153 154 // static SKColorSpaceTransferFn Pq() 155 // { 156 // SKColorSpaceTransferFn fn; 157 // SkiaApi.sk_colorspace_transfer_fn_named_pq (&fn); 158 // return fn; 159 // } 160 161 // static SKColorSpaceTransferFn Hlg() 162 // { 163 // SKColorSpaceTransferFn fn; 164 // SkiaApi.sk_colorspace_transfer_fn_named_hlg (&fn); 165 // return fn; 166 // } 167 168 // static SKColorSpaceTransferFn Empty; 169 170 // this (float[] values) 171 // { 172 // if (values is null) 173 // throw new ArgumentNullException (values.stringof); 174 // if (values.Length != 7) 175 // throw new ArgumentException ("The values must have exactly 7 items, one for each of [G, A, B, C, D, E, F].", values.stringof); 176 177 // fG = values[0]; 178 // fA = values[1]; 179 // fB = values[2]; 180 // fC = values[3]; 181 // fD = values[4]; 182 // fE = values[5]; 183 // fF = values[6]; 184 // } 185 186 // this (float g, float a, float b, float c, float d, float e, float f) 187 // { 188 // fG = g; 189 // fA = a; 190 // fB = b; 191 // fC = c; 192 // fD = d; 193 // fE = e; 194 // fF = f; 195 // } 196 197 // // const float[] Values() 198 // // { 199 // // return new[] { fG, fA, fB, fC, fD, fE, fF }; 200 // // } 201 202 203 // const SKColorSpaceTransferFn Invert () 204 // { 205 // SKColorSpaceTransferFn inverted; 206 // SKColorSpaceTransferFn* t = &this; 207 // SkiaApi.sk_colorspace_transfer_fn_invert (t, &inverted); 208 // return inverted; 209 // } 210 211 // const float Transform (float x) 212 // { 213 // SKColorSpaceTransferFn* t = &this; 214 // return SkiaApi.sk_colorspace_transfer_fn_eval (t, x); 215 // } 216 // } 217 218 // struct SKColorSpaceXyz 219 // { 220 // static SKColorSpaceXyz Srgb() 221 // { 222 // SKColorSpaceXyz xyz; 223 // SkiaApi.sk_colorspace_xyz_named_srgb (&xyz); 224 // return xyz; 225 // } 226 227 // static SKColorSpaceXyz AdobeRgb() 228 // { 229 // SKColorSpaceXyz xyz; 230 // SkiaApi.sk_colorspace_xyz_named_adobe_rgb (&xyz); 231 // return xyz; 232 // } 233 234 // static SKColorSpaceXyz Dcip3() 235 // { 236 // SKColorSpaceXyz xyz; 237 // SkiaApi.sk_colorspace_xyz_named_dcip3 (&xyz); 238 // return xyz; 239 // } 240 241 // static SKColorSpaceXyz Rec2020 () 242 // { 243 // SKColorSpaceXyz xyz; 244 // SkiaApi.sk_colorspace_xyz_named_rec2020 (&xyz); 245 // return xyz; 246 // } 247 248 // static SKColorSpaceXyz Xyz () 249 // { 250 // SKColorSpaceXyz xyz; 251 // SkiaApi.sk_colorspace_xyz_named_xyz (&xyz); 252 // return xyz; 253 // } 254 255 // // static readonly SKColorSpaceXyz Empty; 256 257 // this (float value) 258 // { 259 // fM00 = value; 260 // fM01 = value; 261 // fM02 = value; 262 263 // fM10 = value; 264 // fM11 = value; 265 // fM12 = value; 266 267 // fM20 = value; 268 // fM21 = value; 269 // fM22 = value; 270 // } 271 272 // this (float[] values) 273 // { 274 // if (values is null) 275 // throw new ArgumentNullException (values.stringof); 276 // if (values.Length != 9) 277 // throw new ArgumentException ("The matrix array must have a length of 9.", values.stringof); 278 279 // fM00 = values[0]; 280 // fM01 = values[1]; 281 // fM02 = values[2]; 282 283 // fM10 = values[3]; 284 // fM11 = values[4]; 285 // fM12 = values[5]; 286 287 // fM20 = values[6]; 288 // fM21 = values[7]; 289 // fM22 = values[8]; 290 // } 291 292 // this ( 293 // float m00, float m01, float m02, 294 // float m10, float m11, float m12, 295 // float m20, float m21, float m22) 296 // { 297 // fM00 = m00; 298 // fM01 = m01; 299 // fM02 = m02; 300 301 // fM10 = m10; 302 // fM11 = m11; 303 // fM12 = m12; 304 305 // fM20 = m20; 306 // fM21 = m21; 307 // fM22 = m22; 308 // } 309 310 // // float[] Values() { 311 // // return new float[9] { 312 // // fM00, fM01, fM02, 313 // // fM10, fM11, fM12, 314 // // fM20, fM21, fM22, 315 // // }; 316 // // } 317 318 // void Values(float[] value) { 319 320 // if (value.Length != 9) 321 // throw new ArgumentException ("The matrix array must have a length of 9.", value.stringof); 322 323 // fM00 = value[0]; 324 // fM01 = value[1]; 325 // fM02 = value[2]; 326 327 // fM10 = value[3]; 328 // fM11 = value[4]; 329 // fM12 = value[5]; 330 331 // fM20 = value[6]; 332 // fM21 = value[7]; 333 // fM22 = value[8]; 334 335 // } 336 337 // // const float this[int x, int y] { 338 // // if (x < 0 || x >= 3) 339 // // throw new ArgumentOutOfRangeException (x.stringof); 340 // // if (y < 0 || y >= 3) 341 // // throw new ArgumentOutOfRangeException (y.stringof); 342 343 // // auto idx = x + (y * 3); 344 // // switch(idx) 345 // // { 346 // // case 0:return fM00; 347 // // case 1:return fM01; 348 // // case 2:return fM02; 349 // // case 3:return fM10; 350 // // case 4:return fM11; 351 // // case 5:return fM12; 352 // // case 6:return fM20; 353 // // case 7:return fM21; 354 // // case 8:return fM22; 355 // // default: 356 // // return throw new ArgumentOutOfRangeException ("index"); 357 // // } 358 // // } 359 360 // const SKColorSpaceXyz Invert () 361 // { 362 // SKColorSpaceXyz inverted; 363 // SKColorSpaceXyz* t = &this; 364 // SkiaApi.sk_colorspace_xyz_invert (t, &inverted); 365 // return inverted; 366 // } 367 368 // static SKColorSpaceXyz Concat (SKColorSpaceXyz a, SKColorSpaceXyz b) 369 // { 370 // SKColorSpaceXyz result; 371 // SkiaApi.sk_colorspace_xyz_concat (&a, &b, &result); 372 // return result; 373 // } 374 375 // SKMatrix44 ToMatrix44 () 376 // { 377 // auto matrix = new SKMatrix44 (); 378 // matrix.Set3x3RowMajor (Values); 379 // return matrix; 380 // } 381 // } 382 383 class SKColorSpaceIccProfile : SKObject 384 { 385 this (void* handle, bool owns) 386 { 387 super (handle, owns); 388 } 389 390 this () 391 { 392 this (SkiaApi.sk_colorspace_icc_profile_new (), true); 393 if (Handle is null) 394 throw new InvalidOperationException ("Unable to create a new SK3dView instance."); 395 } 396 397 protected override void DisposeNative () 398 { 399 SkiaApi.sk_colorspace_icc_profile_delete (cast(sk_colorspace_icc_profile_t*)Handle); 400 } 401 402 403 // properties 404 405 long Size() { 406 407 uint size; 408 SkiaApi.sk_colorspace_icc_profile_get_buffer (cast(sk_colorspace_icc_profile_t*)Handle, &size); 409 return size; 410 411 } 412 413 void* Buffer() 414 { 415 return cast(void*)SkiaApi.sk_colorspace_icc_profile_get_buffer (cast(sk_colorspace_icc_profile_t*)Handle, null); 416 } 417 418 419 // ToColorSpaceXyz 420 421 bool ToColorSpaceXyz (out SKColorSpaceXyz toXyzD50) 422 { 423 SKColorSpaceXyz* xyz = &toXyzD50; 424 return SkiaApi.sk_colorspace_icc_profile_get_to_xyzd50 (cast(sk_colorspace_icc_profile_t*)Handle, xyz); 425 } 426 427 SKColorSpaceXyz ToColorSpaceXyz () 428 { 429 SKColorSpaceXyz toXYZ; 430 return ToColorSpaceXyz (toXYZ) ? toXYZ : SKColorSpaceXyz.Empty; 431 } 432 433 434 // Create 435 436 // static SKColorSpaceIccProfile Create (byte[] data) 437 // { 438 // return Create (data); 439 // } 440 441 442 static SKColorSpaceIccProfile Create (byte[] data) 443 { 444 if (data.empty) 445 return null; 446 447 SKData skData = SKData.CreateCopy (data); 448 auto icc = Create (skData); 449 if (icc is null) 450 skData.Dispose (); 451 return icc; 452 } 453 454 static SKColorSpaceIccProfile Create (SKData data) 455 { 456 if (data is null) 457 throw new ArgumentNullException (data.stringof); 458 459 if (data.IsEmpty) 460 return null; 461 462 return Referenced (Create (data.Data, data.Size), data); 463 } 464 465 static SKColorSpaceIccProfile Create (void* data, long length) 466 { 467 if (data is null) 468 throw new ArgumentNullException (data.stringof); 469 470 if (length <= 0) 471 return null; 472 473 auto icc = new SKColorSpaceIccProfile (); 474 if (!SkiaApi.sk_colorspace_icc_profile_parse (cast(void*)data, cast(size_t)length, cast(sk_colorspace_icc_profile_t*)icc.Handle)) { 475 icc.Dispose (); 476 icc = null; 477 } 478 return icc; 479 } 480 }