| OLD | NEW |
| (Empty) |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | |
| 2 // for details. All rights reserved. Use of this source code is governed by a | |
| 3 // BSD-style license that can be found in the LICENSE file. | |
| 4 | |
| 5 /** | |
| 6 * Specialized integers and floating point numbers, | |
| 7 * with SIMD support and efficient lists. | |
| 8 */ | |
| 9 library dart.typed_data; | |
| 10 | |
| 11 import 'dart:collection' show ListMixin; | |
| 12 import 'dart:_internal' show FixedLengthListMixin; | |
| 13 import 'dart:_native_typed_data'; | |
| 14 import 'dart:_foreign_helper' show JS; | |
| 15 import 'dart:math' as Math; | |
| 16 | |
| 17 export 'dart:_native_typed_data' show Endianness; | |
| 18 | |
| 19 | |
| 20 /** | |
| 21 * A sequence of bytes underlying a typed data object. | |
| 22 * Used to process large quantities of binary or numerical data | |
| 23 * more efficiently using a typed view. | |
| 24 */ | |
| 25 abstract class ByteBuffer { | |
| 26 int get lengthInBytes; | |
| 27 | |
| 28 /** | |
| 29 * Creates a new [Uint8List] view of this buffer. | |
| 30 */ | |
| 31 Uint8List asUint8List([int offsetInBytes = 0, int length]); | |
| 32 /** | |
| 33 * Creates a new [Int8List] view of this buffer. | |
| 34 */ | |
| 35 Int8List asInt8List([int offsetInBytes = 0, int length]); | |
| 36 /** | |
| 37 * Creates a new [Uint8Clamped] view of this buffer. | |
| 38 */ | |
| 39 Uint8ClampedList asUint8ClampedList([int offsetInBytes = 0, int length]); | |
| 40 /** | |
| 41 * Creates a new [Uint16List] view of this buffer. | |
| 42 */ | |
| 43 Uint16List asUint16List([int offsetInBytes = 0, int length]); | |
| 44 /** | |
| 45 * Creates a new [Int16List] view of this buffer. | |
| 46 */ | |
| 47 Int16List asInt16List([int offsetInBytes = 0, int length]); | |
| 48 /** | |
| 49 * Creates a new [Uint32List] view of this buffer. | |
| 50 */ | |
| 51 Uint32List asUint32List([int offsetInBytes = 0, int length]); | |
| 52 /** | |
| 53 * Creates a new [Int32List] view of this buffer. | |
| 54 */ | |
| 55 Int32List asInt32List([int offsetInBytes = 0, int length]); | |
| 56 /** | |
| 57 * Creates a new [Uint64List] view of this buffer. | |
| 58 */ | |
| 59 Uint64List asUint64List([int offsetInBytes = 0, int length]); | |
| 60 /** | |
| 61 * Creates a new [Int64List] view of this buffer. | |
| 62 */ | |
| 63 Int64List asInt64List([int offsetInBytes = 0, int length]); | |
| 64 /** | |
| 65 * Creates a new [Int32x4List] view of this buffer. | |
| 66 */ | |
| 67 Int32x4List asInt32x4List([int offsetInBytes = 0, int length]); | |
| 68 /** | |
| 69 * Creates a new [Float32List] view of this buffer. | |
| 70 */ | |
| 71 Float32List asFloat32List([int offsetInBytes = 0, int length]); | |
| 72 /** | |
| 73 * Creates a new [Float64List] view of this buffer. | |
| 74 */ | |
| 75 Float64List asFloat64List([int offsetInBytes = 0, int length]); | |
| 76 /** | |
| 77 * Creates a new [Float32x4List] view of this buffer. | |
| 78 */ | |
| 79 Float32x4List asFloat32x4List([int offsetInBytes = 0, int length]); | |
| 80 /** | |
| 81 * Creates a new [Float64x2List] view of this buffer. | |
| 82 */ | |
| 83 Float64x2List asFloat64x2List([int offsetInBytes = 0, int length]); | |
| 84 /** | |
| 85 * Creates a new [ByteData] view of this buffer. | |
| 86 */ | |
| 87 ByteData asByteData([int offsetInBytes = 0, int length]); | |
| 88 } | |
| 89 | |
| 90 | |
| 91 /** | |
| 92 * A typed view of a sequence of bytes. | |
| 93 */ | |
| 94 abstract class TypedData { | |
| 95 /** | |
| 96 * Returns the byte buffer associated with this object. | |
| 97 */ | |
| 98 ByteBuffer get buffer; | |
| 99 | |
| 100 /** | |
| 101 * Returns the length of this view, in bytes. | |
| 102 */ | |
| 103 int get lengthInBytes; | |
| 104 | |
| 105 /** | |
| 106 * Returns the offset in bytes into the underlying byte buffer of this view. | |
| 107 */ | |
| 108 int get offsetInBytes; | |
| 109 | |
| 110 /** | |
| 111 * Returns the number of bytes in the representation of each element in this | |
| 112 * list. | |
| 113 */ | |
| 114 int get elementSizeInBytes; | |
| 115 } | |
| 116 | |
| 117 | |
| 118 /** | |
| 119 * A fixed-length, random-access sequence of bytes that also provides random | |
| 120 * and unaligned access to the fixed-width integers and floating point | |
| 121 * numbers represented by those bytes. | |
| 122 * ByteData may be used to pack and unpack data from external sources | |
| 123 * (such as networks or files systems), and to process large quantities | |
| 124 * of numerical data more efficiently than would be possible | |
| 125 * with ordinary [List] implementations. ByteData can save space, by | |
| 126 * eliminating the need for object headers, and time, by eliminating the | |
| 127 * need for data copies. Finally, ByteData may be used to intentionally | |
| 128 * reinterpret the bytes representing one arithmetic type as another. | |
| 129 * For example this code fragment determine what 32-bit signed integer | |
| 130 * is represented by the bytes of a 32-bit floating point number: | |
| 131 * | |
| 132 * var buffer = new Uint8List(8).buffer; | |
| 133 * var bdata = new ByteData.view(buffer); | |
| 134 * bdata.setFloat32(0, 3.04); | |
| 135 * int huh = bdata.getInt32(0); | |
| 136 */ | |
| 137 abstract class ByteData extends TypedData { | |
| 138 /** | |
| 139 * Creates a [ByteData] of the specified length (in elements), all of | |
| 140 * whose elements are initially zero. | |
| 141 */ | |
| 142 factory ByteData(int length) => new NativeByteData(length); | |
| 143 | |
| 144 /** | |
| 145 * Creates an [ByteData] _view_ of the specified region in the specified | |
| 146 * byte buffer. Changes in the [ByteData] will be visible in the byte | |
| 147 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 148 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 149 * If the length is not specified, it defaults to null, which indicates | |
| 150 * that the view extends to the end of the byte buffer. | |
| 151 * | |
| 152 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 153 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 154 * the length of [buffer]. | |
| 155 */ | |
| 156 factory ByteData.view(ByteBuffer buffer, | |
| 157 [int offsetInBytes = 0, int length]) => | |
| 158 buffer.asByteData(offsetInBytes, length); | |
| 159 | |
| 160 int get elementSizeInBytes => 1; | |
| 161 | |
| 162 /** | |
| 163 * Returns the floating point number represented by the four bytes at | |
| 164 * the specified [byteOffset] in this object, in IEEE 754 | |
| 165 * single-precision binary floating-point format (binary32). | |
| 166 * | |
| 167 * Throws [RangeError] if [byteOffset] is negative, or | |
| 168 * `byteOffset + 4` is greater than the length of this object. | |
| 169 */ | |
| 170 num getFloat32(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 171 | |
| 172 /** | |
| 173 * Returns the floating point number represented by the eight bytes at | |
| 174 * the specified [byteOffset] in this object, in IEEE 754 | |
| 175 * double-precision binary floating-point format (binary64). | |
| 176 * | |
| 177 * Throws [RangeError] if [byteOffset] is negative, or | |
| 178 * `byteOffset + 8` is greater than the length of this object. | |
| 179 */ | |
| 180 num getFloat64(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 181 | |
| 182 /** | |
| 183 * Returns the (possibly negative) integer represented by the two bytes at | |
| 184 * the specified [byteOffset] in this object, in two's complement binary | |
| 185 * form. | |
| 186 * The return value will be between 2<sup>15</sup> and 2<sup>15</sup> - 1, | |
| 187 * inclusive. | |
| 188 * | |
| 189 * Throws [RangeError] if [byteOffset] is negative, or | |
| 190 * `byteOffset + 2` is greater than the length of this object. | |
| 191 */ | |
| 192 int getInt16(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 193 | |
| 194 /** | |
| 195 * Returns the (possibly negative) integer represented by the four bytes at | |
| 196 * the specified [byteOffset] in this object, in two's complement binary | |
| 197 * form. | |
| 198 * The return value will be between 2<sup>31</sup> and 2<sup>31</sup> - 1, | |
| 199 * inclusive. | |
| 200 * | |
| 201 * Throws [RangeError] if [byteOffset] is negative, or | |
| 202 * `byteOffset + 4` is greater than the length of this object. | |
| 203 */ | |
| 204 int getInt32(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 205 | |
| 206 /** | |
| 207 * Returns the (possibly negative) integer represented by the eight bytes at | |
| 208 * the specified [byteOffset] in this object, in two's complement binary | |
| 209 * form. | |
| 210 * The return value will be between 2<sup>63</sup> and 2<sup>63</sup> - 1, | |
| 211 * inclusive. | |
| 212 * | |
| 213 * Throws [RangeError] if [byteOffset] is negative, or | |
| 214 * `byteOffset + 8` is greater than the length of this object. | |
| 215 */ | |
| 216 int getInt64(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 217 | |
| 218 /** | |
| 219 * Returns the (possibly negative) integer represented by the byte at the | |
| 220 * specified [byteOffset] in this object, in two's complement binary | |
| 221 * representation. The return value will be between -128 and 127, inclusive. | |
| 222 * | |
| 223 * Throws [RangeError] if [byteOffset] is negative, or | |
| 224 * greater than or equal to the length of this object. | |
| 225 */ | |
| 226 int getInt8(int byteOffset) ; | |
| 227 | |
| 228 /** | |
| 229 * Returns the positive integer represented by the two bytes starting | |
| 230 * at the specified [byteOffset] in this object, in unsigned binary | |
| 231 * form. | |
| 232 * The return value will be between 0 and 2<sup>16</sup> - 1, inclusive. | |
| 233 * | |
| 234 * Throws [RangeError] if [byteOffset] is negative, or | |
| 235 * `byteOffset + 2` is greater than the length of this object. | |
| 236 */ | |
| 237 int getUint16(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 238 | |
| 239 /** | |
| 240 * Returns the positive integer represented by the four bytes starting | |
| 241 * at the specified [byteOffset] in this object, in unsigned binary | |
| 242 * form. | |
| 243 * The return value will be between 0 and 2<sup>32</sup> - 1, inclusive. | |
| 244 * | |
| 245 * Throws [RangeError] if [byteOffset] is negative, or | |
| 246 * `byteOffset + 4` is greater than the length of this object. | |
| 247 */ | |
| 248 int getUint32(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 249 | |
| 250 /** | |
| 251 * Returns the positive integer represented by the eight bytes starting | |
| 252 * at the specified [byteOffset] in this object, in unsigned binary | |
| 253 * form. | |
| 254 * The return value will be between 0 and 2<sup>64</sup> - 1, inclusive. | |
| 255 * | |
| 256 * Throws [RangeError] if [byteOffset] is negative, or | |
| 257 * `byteOffset + 8` is greater than the length of this object. | |
| 258 */ | |
| 259 int getUint64(int byteOffset, [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 260 | |
| 261 /** | |
| 262 * Returns the positive integer represented by the byte at the specified | |
| 263 * [byteOffset] in this object, in unsigned binary form. The | |
| 264 * return value will be between 0 and 255, inclusive. | |
| 265 * | |
| 266 * Throws [RangeError] if [byteOffset] is negative, or | |
| 267 * greater than or equal to the length of this object. | |
| 268 */ | |
| 269 int getUint8(int byteOffset); | |
| 270 | |
| 271 /** | |
| 272 * Sets the four bytes starting at the specified [byteOffset] in this | |
| 273 * object to the IEEE 754 single-precision binary floating-point | |
| 274 * (binary32) representation of the specified [value]. | |
| 275 * | |
| 276 * **Note that this method can lose precision.** The input [value] is | |
| 277 * a 64-bit floating point value, which will be converted to 32-bit | |
| 278 * floating point value by IEEE 754 rounding rules before it is stored. | |
| 279 * If [value] cannot be represented exactly as a binary32, it will be | |
| 280 * converted to the nearest binary32 value. If two binary32 values are | |
| 281 * equally close, the one whose least significant bit is zero will be used. | |
| 282 * Note that finite (but large) values can be converted to infinity, and | |
| 283 * small non-zero values can be converted to zero. | |
| 284 * | |
| 285 * Throws [RangeError] if [byteOffset] is negative, or | |
| 286 * `byteOffset + 4` is greater than the length of this object. | |
| 287 */ | |
| 288 void setFloat32(int byteOffset, num value, | |
| 289 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 290 | |
| 291 /** | |
| 292 * Sets the eight bytes starting at the specified [byteOffset] in this | |
| 293 * object to the IEEE 754 double-precision binary floating-point | |
| 294 * (binary64) representation of the specified [value]. | |
| 295 * | |
| 296 * Throws [RangeError] if [byteOffset] is negative, or | |
| 297 * `byteOffset + 8` is greater than the length of this object. | |
| 298 */ | |
| 299 void setFloat64(int byteOffset, num value, | |
| 300 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 301 | |
| 302 /** | |
| 303 * Sets the two bytes starting at the specified [byteOffset] in this | |
| 304 * object to the two's complement binary representation of the specified | |
| 305 * [value], which must fit in two bytes. In other words, [value] must lie | |
| 306 * between 2<sup>15</sup> and 2<sup>15</sup> - 1, inclusive. | |
| 307 * | |
| 308 * Throws [RangeError] if [byteOffset] is negative, or | |
| 309 * `byteOffset + 2` is greater than the length of this object. | |
| 310 */ | |
| 311 void setInt16(int byteOffset, int value, | |
| 312 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 313 | |
| 314 /** | |
| 315 * Sets the four bytes starting at the specified [byteOffset] in this | |
| 316 * object to the two's complement binary representation of the specified | |
| 317 * [value], which must fit in four bytes. In other words, [value] must lie | |
| 318 * between 2<sup>31</sup> and 2<sup>31</sup> - 1, inclusive. | |
| 319 * | |
| 320 * Throws [RangeError] if [byteOffset] is negative, or | |
| 321 * `byteOffset + 4` is greater than the length of this object. | |
| 322 */ | |
| 323 void setInt32(int byteOffset, int value, | |
| 324 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 325 | |
| 326 /** | |
| 327 * Sets the eight bytes starting at the specified [byteOffset] in this | |
| 328 * object to the two's complement binary representation of the specified | |
| 329 * [value], which must fit in eight bytes. In other words, [value] must lie | |
| 330 * between 2<sup>63</sup> and 2<sup>63</sup> - 1, inclusive. | |
| 331 * | |
| 332 * Throws [RangeError] if [byteOffset] is negative, or | |
| 333 * `byteOffset + 8` is greater than the length of this object. | |
| 334 */ | |
| 335 void setInt64(int byteOffset, int value, | |
| 336 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 337 | |
| 338 /** | |
| 339 * Sets the byte at the specified [byteOffset] in this object to the | |
| 340 * two's complement binary representation of the specified [value], which | |
| 341 * must fit in a single byte. In other words, [value] must be between | |
| 342 * -128 and 127, inclusive. | |
| 343 * | |
| 344 * Throws [RangeError] if [byteOffset] is negative, or | |
| 345 * greater than or equal to the length of this object. | |
| 346 */ | |
| 347 void setInt8(int byteOffset, int value); | |
| 348 | |
| 349 /** | |
| 350 * Sets the two bytes starting at the specified [byteOffset] in this object | |
| 351 * to the unsigned binary representation of the specified [value], | |
| 352 * which must fit in two bytes. in other words, [value] must be between | |
| 353 * 0 and 2<sup>16</sup> - 1, inclusive. | |
| 354 * | |
| 355 * Throws [RangeError] if [byteOffset] is negative, or | |
| 356 * `byteOffset + 2` is greater than the length of this object. | |
| 357 */ | |
| 358 void setUint16(int byteOffset, int value, | |
| 359 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 360 | |
| 361 /** | |
| 362 * Sets the four bytes starting at the specified [byteOffset] in this object | |
| 363 * to the unsigned binary representation of the specified [value], | |
| 364 * which must fit in four bytes. in other words, [value] must be between | |
| 365 * 0 and 2<sup>32</sup> - 1, inclusive. | |
| 366 * | |
| 367 * Throws [RangeError] if [byteOffset] is negative, or | |
| 368 * `byteOffset + 4` is greater than the length of this object. | |
| 369 */ | |
| 370 void setUint32(int byteOffset, int value, | |
| 371 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 372 | |
| 373 /** | |
| 374 * Sets the eight bytes starting at the specified [byteOffset] in this object | |
| 375 * to the unsigned binary representation of the specified [value], | |
| 376 * which must fit in eight bytes. in other words, [value] must be between | |
| 377 * 0 and 2<sup>64</sup> - 1, inclusive. | |
| 378 * | |
| 379 * Throws [RangeError] if [byteOffset] is negative, or | |
| 380 * `byteOffset + 8` is greater than the length of this object. | |
| 381 */ | |
| 382 void setUint64(int byteOffset, int value, | |
| 383 [Endianness endian=Endianness.BIG_ENDIAN]); | |
| 384 | |
| 385 /** | |
| 386 * Sets the byte at the specified [byteOffset] in this object to the | |
| 387 * unsigned binary representation of the specified [value], which must fit | |
| 388 * in a single byte. in other words, [value] must be between 0 and 255, | |
| 389 * inclusive. | |
| 390 * | |
| 391 * Throws [RangeError] if [byteOffset] is negative, | |
| 392 * or greater than or equal to the length of this object. | |
| 393 */ | |
| 394 void setUint8(int byteOffset, int value); | |
| 395 } | |
| 396 | |
| 397 | |
| 398 /** | |
| 399 * A fixed-length list of IEEE 754 single-precision binary floating-point | |
| 400 * numbers that is viewable as a [TypedData]. For long lists, this | |
| 401 * implementation can be considerably more space- and time-efficient than | |
| 402 * the default [List] implementation. | |
| 403 */ | |
| 404 abstract class Float32List implements TypedData, List<double> { | |
| 405 /** | |
| 406 * Creates a [Float32List] of the specified length (in elements), all of | |
| 407 * whose elements are initially zero. | |
| 408 */ | |
| 409 factory Float32List(int length) = NativeFloat32List; | |
| 410 | |
| 411 /** | |
| 412 * Creates a [Float32List] with the same size as the [elements] list | |
| 413 * and copies over the elements. | |
| 414 */ | |
| 415 factory Float32List.fromList(List<double> elements) => | |
| 416 new NativeFloat32List.fromList(elements); | |
| 417 | |
| 418 /** | |
| 419 * Creates a [Float32List] _view_ of the specified region in the specified | |
| 420 * byte buffer. Changes in the [Float32List] will be visible in the byte | |
| 421 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 422 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 423 * If the length is not specified, it defaults to null, which indicates | |
| 424 * that the view extends to the end of the byte buffer. | |
| 425 * | |
| 426 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 427 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 428 * the length of [buffer]. | |
| 429 * | |
| 430 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 431 * BYTES_PER_ELEMENT. | |
| 432 */ | |
| 433 factory Float32List.view(ByteBuffer buffer, | |
| 434 [int offsetInBytes = 0, int length]) => | |
| 435 buffer.asFloat32List(offsetInBytes, length); | |
| 436 | |
| 437 static const int BYTES_PER_ELEMENT = 4; | |
| 438 } | |
| 439 | |
| 440 | |
| 441 /** | |
| 442 * A fixed-length list of IEEE 754 double-precision binary floating-point | |
| 443 * numbers that is viewable as a [TypedData]. For long lists, this | |
| 444 * implementation can be considerably more space- and time-efficient than | |
| 445 * the default [List] implementation. | |
| 446 */ | |
| 447 abstract class Float64List implements TypedData, List<double> { | |
| 448 /** | |
| 449 * Creates a [Float64List] of the specified length (in elements), all of | |
| 450 * whose elements are initially zero. | |
| 451 */ | |
| 452 factory Float64List(int length) = NativeFloat64List; | |
| 453 | |
| 454 /** | |
| 455 * Creates a [Float64List] with the same size as the [elements] list | |
| 456 * and copies over the elements. | |
| 457 */ | |
| 458 factory Float64List.fromList(List<double> elements) => | |
| 459 new NativeFloat64List.fromList(elements); | |
| 460 | |
| 461 /** | |
| 462 * Creates a [Float64List] _view_ of the specified region in the specified | |
| 463 * byte buffer. Changes in the [Float64List] will be visible in the byte | |
| 464 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 465 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 466 * If the length is not specified, it defaults to null, which indicates | |
| 467 * that the view extends to the end of the byte buffer. | |
| 468 * | |
| 469 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 470 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 471 * the length of [buffer]. | |
| 472 * | |
| 473 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 474 * BYTES_PER_ELEMENT. | |
| 475 */ | |
| 476 factory Float64List.view(ByteBuffer buffer, | |
| 477 [int offsetInBytes = 0, int length]) => | |
| 478 buffer.asFloat64List(offsetInBytes, length); | |
| 479 | |
| 480 static const int BYTES_PER_ELEMENT = 8; | |
| 481 } | |
| 482 | |
| 483 | |
| 484 /** | |
| 485 * A fixed-length list of 16-bit signed integers that is viewable as a | |
| 486 * [TypedData]. For long lists, this implementation can be considerably | |
| 487 * more space- and time-efficient than the default [List] implementation. | |
| 488 */ | |
| 489 abstract class Int16List extends TypedData implements List<int> { | |
| 490 /** | |
| 491 * Creates an [Int16List] of the specified length (in elements), all of | |
| 492 * whose elements are initially zero. | |
| 493 */ | |
| 494 factory Int16List(int length) = NativeInt16List; | |
| 495 | |
| 496 /** | |
| 497 * Creates a [Int16List] with the same size as the [elements] list | |
| 498 * and copies over the elements. | |
| 499 */ | |
| 500 factory Int16List.fromList(List<int> elements) => | |
| 501 new NativeInt16List.fromList(elements); | |
| 502 | |
| 503 /** | |
| 504 * Creates an [Int16List] _view_ of the specified region in the specified | |
| 505 * byte buffer. Changes in the [Int16List] will be visible in the byte | |
| 506 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 507 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 508 * If the length is not specified, it defaults to null, which indicates | |
| 509 * that the view extends to the end of the byte buffer. | |
| 510 * | |
| 511 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 512 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 513 * the length of [buffer]. | |
| 514 * | |
| 515 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 516 * BYTES_PER_ELEMENT. | |
| 517 */ | |
| 518 factory Int16List.view(ByteBuffer buffer, | |
| 519 [int offsetInBytes = 0, int length]) => | |
| 520 buffer.asInt16List(offsetInBytes, length); | |
| 521 | |
| 522 static const int BYTES_PER_ELEMENT = 2; | |
| 523 } | |
| 524 | |
| 525 | |
| 526 /** | |
| 527 * A fixed-length list of 32-bit signed integers that is viewable as a | |
| 528 * [TypedData]. For long lists, this implementation can be considerably | |
| 529 * more space- and time-efficient than the default [List] implementation. | |
| 530 */ | |
| 531 abstract class Int32List implements TypedData, List<int> { | |
| 532 /** | |
| 533 * Creates an [Int32List] of the specified length (in elements), all of | |
| 534 * whose elements are initially zero. | |
| 535 */ | |
| 536 factory Int32List(int length) = NativeInt32List; | |
| 537 | |
| 538 /** | |
| 539 * Creates a [Int32List] with the same size as the [elements] list | |
| 540 * and copies over the elements. | |
| 541 */ | |
| 542 factory Int32List.fromList(List<int> elements) => | |
| 543 new NativeInt32List.fromList(elements); | |
| 544 | |
| 545 /** | |
| 546 * Creates an [Int32List] _view_ of the specified region in the specified | |
| 547 * byte buffer. Changes in the [Int32List] will be visible in the byte | |
| 548 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 549 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 550 * If the length is not specified, it defaults to null, which indicates | |
| 551 * that the view extends to the end of the byte buffer. | |
| 552 * | |
| 553 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 554 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 555 * the length of [buffer]. | |
| 556 * | |
| 557 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 558 * BYTES_PER_ELEMENT. | |
| 559 */ | |
| 560 factory Int32List.view(ByteBuffer buffer, | |
| 561 [int offsetInBytes = 0, int length]) => | |
| 562 buffer.asInt32List(offsetInBytes, length); | |
| 563 | |
| 564 static const int BYTES_PER_ELEMENT = 4; | |
| 565 } | |
| 566 | |
| 567 | |
| 568 /** | |
| 569 * A fixed-length list of 8-bit signed integers. | |
| 570 * For long lists, this implementation can be considerably | |
| 571 * more space- and time-efficient than the default [List] implementation. | |
| 572 */ | |
| 573 abstract class Int8List implements TypedData, List<int> { | |
| 574 /** | |
| 575 * Creates an [Int8List] of the specified length (in elements), all of | |
| 576 * whose elements are initially zero. | |
| 577 */ | |
| 578 factory Int8List(int length) = NativeInt8List; | |
| 579 | |
| 580 /** | |
| 581 * Creates a [Int8List] with the same size as the [elements] list | |
| 582 * and copies over the elements. | |
| 583 */ | |
| 584 factory Int8List.fromList(List<int> elements) => | |
| 585 new NativeInt8List.fromList(elements); | |
| 586 | |
| 587 /** | |
| 588 * Creates an [Int8List] _view_ of the specified region in the specified | |
| 589 * byte buffer. Changes in the [Int8List] will be visible in the byte | |
| 590 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 591 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 592 * If the length is not specified, it defaults to null, which indicates | |
| 593 * that the view extends to the end of the byte buffer. | |
| 594 * | |
| 595 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 596 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 597 * the length of [buffer]. | |
| 598 */ | |
| 599 factory Int8List.view(ByteBuffer buffer, | |
| 600 [int offsetInBytes = 0, int length]) => | |
| 601 buffer.asInt8List(offsetInBytes, length); | |
| 602 | |
| 603 static const int BYTES_PER_ELEMENT = 1; | |
| 604 } | |
| 605 | |
| 606 | |
| 607 /** | |
| 608 * A fixed-length list of 16-bit unsigned integers that is viewable as a | |
| 609 * [TypedData]. For long lists, this implementation can be considerably | |
| 610 * more space- and time-efficient than the default [List] implementation. | |
| 611 */ | |
| 612 abstract class Uint16List implements TypedData, List<int> { | |
| 613 /** | |
| 614 * Creates a [Uint16List] of the specified length (in elements), all | |
| 615 * of whose elements are initially zero. | |
| 616 */ | |
| 617 factory Uint16List(int length) = NativeUint16List; | |
| 618 | |
| 619 /** | |
| 620 * Creates a [Uint16List] with the same size as the [elements] list | |
| 621 * and copies over the elements. | |
| 622 */ | |
| 623 factory Uint16List.fromList(List<int> elements) => | |
| 624 new NativeUint16List.fromList(elements); | |
| 625 | |
| 626 /** | |
| 627 * Creates a [Uint16List] _view_ of the specified region in | |
| 628 * the specified byte buffer. Changes in the [Uint16List] will be | |
| 629 * visible in the byte buffer and vice versa. If the [offsetInBytes] index | |
| 630 * of the region is not specified, it defaults to zero (the first byte in | |
| 631 * the byte buffer). If the length is not specified, it defaults to null, | |
| 632 * which indicates that the view extends to the end of the byte buffer. | |
| 633 * | |
| 634 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 635 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 636 * the length of [buffer]. | |
| 637 * | |
| 638 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 639 * BYTES_PER_ELEMENT. | |
| 640 */ | |
| 641 factory Uint16List.view(ByteBuffer buffer, | |
| 642 [int offsetInBytes = 0, int length]) => | |
| 643 buffer.asUint16List(offsetInBytes, length); | |
| 644 | |
| 645 static const int BYTES_PER_ELEMENT = 2; | |
| 646 } | |
| 647 | |
| 648 | |
| 649 /** | |
| 650 * A fixed-length list of 32-bit unsigned integers that is viewable as a | |
| 651 * [TypedData]. For long lists, this implementation can be considerably | |
| 652 * more space- and time-efficient than the default [List] implementation. | |
| 653 */ | |
| 654 abstract class Uint32List implements TypedData, List<int> { | |
| 655 /** | |
| 656 * Creates a [Uint32List] of the specified length (in elements), all | |
| 657 * of whose elements are initially zero. | |
| 658 */ | |
| 659 factory Uint32List(int length) = NativeUint32List; | |
| 660 | |
| 661 /** | |
| 662 * Creates a [Uint32List] with the same size as the [elements] list | |
| 663 * and copies over the elements. | |
| 664 */ | |
| 665 factory Uint32List.fromList(List<int> elements) => | |
| 666 new NativeUint32List.fromList(elements); | |
| 667 | |
| 668 /** | |
| 669 * Creates a [Uint32List] _view_ of the specified region in | |
| 670 * the specified byte buffer. Changes in the [Uint32] will be | |
| 671 * visible in the byte buffer and vice versa. If the [offsetInBytes] index | |
| 672 * of the region is not specified, it defaults to zero (the first byte in | |
| 673 * the byte buffer). If the length is not specified, it defaults to null, | |
| 674 * which indicates that the view extends to the end of the byte buffer. | |
| 675 * | |
| 676 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 677 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 678 * the length of [buffer]. | |
| 679 * | |
| 680 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 681 * BYTES_PER_ELEMENT. | |
| 682 */ | |
| 683 factory Uint32List.view(ByteBuffer buffer, | |
| 684 [int offsetInBytes = 0, int length]) => | |
| 685 buffer.asUint32List(offsetInBytes, length); | |
| 686 | |
| 687 static const int BYTES_PER_ELEMENT = 4; | |
| 688 } | |
| 689 | |
| 690 | |
| 691 /** | |
| 692 * A fixed-length list of 8-bit unsigned integers. | |
| 693 * For long lists, this implementation can be considerably | |
| 694 * more space- and time-efficient than the default [List] implementation. | |
| 695 * Indexed store clamps the value to range 0..0xFF. | |
| 696 */ | |
| 697 abstract class Uint8ClampedList implements TypedData, List<int> { | |
| 698 /** | |
| 699 * Creates a [Uint8ClampedList] of the specified length (in elements), all of | |
| 700 * whose elements are initially zero. | |
| 701 */ | |
| 702 factory Uint8ClampedList(int length) = NativeUint8ClampedList; | |
| 703 | |
| 704 /** | |
| 705 * Creates a [Uint8ClampedList] of the same size as the [elements] | |
| 706 * list and copies over the values clamping when needed. | |
| 707 */ | |
| 708 factory Uint8ClampedList.fromList(List<int> elements) => | |
| 709 new NativeUint8ClampedList.fromList(elements); | |
| 710 | |
| 711 /** | |
| 712 * Creates a [Uint8ClampedList] _view_ of the specified region in the | |
| 713 * specified byte [buffer]. Changes in the [Uint8List] will be visible in the | |
| 714 * byte buffer and vice versa. If the [offsetInBytes] index of the region is | |
| 715 * not specified, it defaults to zero (the first byte in the byte buffer). | |
| 716 * If the length is not specified, it defaults to null, which indicates that | |
| 717 * the view extends to the end of the byte buffer. | |
| 718 * | |
| 719 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 720 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 721 * the length of [buffer]. | |
| 722 */ | |
| 723 factory Uint8ClampedList.view(ByteBuffer buffer, | |
| 724 [int offsetInBytes = 0, int length]) => | |
| 725 buffer.asUint8ClampedList(offsetInBytes, length); | |
| 726 | |
| 727 static const int BYTES_PER_ELEMENT = 1; | |
| 728 } | |
| 729 | |
| 730 | |
| 731 /** | |
| 732 * A fixed-length list of 8-bit unsigned integers. | |
| 733 * For long lists, this implementation can be considerably | |
| 734 * more space- and time-efficient than the default [List] implementation. | |
| 735 */ | |
| 736 abstract class Uint8List implements TypedData, List<int> { | |
| 737 /** | |
| 738 * Creates a [Uint8List] of the specified length (in elements), all of | |
| 739 * whose elements are initially zero. | |
| 740 */ | |
| 741 factory Uint8List(int length) = NativeUint8List; | |
| 742 | |
| 743 /** | |
| 744 * Creates a [Uint8List] with the same size as the [elements] list | |
| 745 * and copies over the elements. | |
| 746 */ | |
| 747 factory Uint8List.fromList(List<int> elements) => | |
| 748 new NativeUint8List.fromList(elements); | |
| 749 | |
| 750 /** | |
| 751 * Creates a [Uint8List] _view_ of the specified region in the specified | |
| 752 * byte buffer. Changes in the [Uint8List] will be visible in the byte | |
| 753 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 754 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 755 * If the length is not specified, it defaults to null, which indicates | |
| 756 * that the view extends to the end of the byte buffer. | |
| 757 * | |
| 758 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 759 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 760 * the length of [buffer]. | |
| 761 */ | |
| 762 factory Uint8List.view(ByteBuffer buffer, | |
| 763 [int offsetInBytes = 0, int length]) => | |
| 764 buffer.asUint8List(offsetInBytes, length); | |
| 765 | |
| 766 static const int BYTES_PER_ELEMENT = 1; | |
| 767 } | |
| 768 | |
| 769 | |
| 770 /** | |
| 771 * A fixed-length list of 64-bit signed integers that is viewable as a | |
| 772 * [TypedData]. For long lists, this implementation can be considerably | |
| 773 * more space- and time-efficient than the default [List] implementation. | |
| 774 */ | |
| 775 abstract class Int64List extends TypedData implements List<int> { | |
| 776 /** | |
| 777 * Creates an [Int64List] of the specified length (in elements), all of | |
| 778 * whose elements are initially zero. | |
| 779 */ | |
| 780 factory Int64List(int length) { | |
| 781 throw new UnsupportedError("Int64List not supported by dart2js."); | |
| 782 } | |
| 783 | |
| 784 /** | |
| 785 * Creates a [Int64List] with the same size as the [elements] list | |
| 786 * and copies over the elements. | |
| 787 */ | |
| 788 factory Int64List.fromList(List<int> list) { | |
| 789 throw new UnsupportedError("Int64List not supported by dart2js."); | |
| 790 } | |
| 791 | |
| 792 /** | |
| 793 * Creates an [Int64List] _view_ of the specified region in the specified | |
| 794 * byte buffer. Changes in the [Int64List] will be visible in the byte buffer | |
| 795 * and vice versa. If the [offsetInBytes] index of the region is not | |
| 796 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 797 * If the length is not specified, it defaults to null, which indicates that | |
| 798 * the view extends to the end of the byte buffer. | |
| 799 * | |
| 800 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 801 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 802 * the length of [buffer]. | |
| 803 * | |
| 804 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 805 * BYTES_PER_ELEMENT. | |
| 806 */ | |
| 807 factory Int64List.view(ByteBuffer buffer, [int byteOffset, int length]) { | |
| 808 throw new UnsupportedError("Int64List not supported by dart2js."); | |
| 809 } | |
| 810 | |
| 811 static const int BYTES_PER_ELEMENT = 8; | |
| 812 } | |
| 813 | |
| 814 | |
| 815 /** | |
| 816 * A fixed-length list of 64-bit unsigned integers that is viewable as a | |
| 817 * [TypedData]. For long lists, this implementation can be considerably | |
| 818 * more space- and time-efficient than the default [List] implementation. | |
| 819 */ | |
| 820 abstract class Uint64List extends TypedData implements List<int> { | |
| 821 /** | |
| 822 * Creates a [Uint64List] of the specified length (in elements), all | |
| 823 * of whose elements are initially zero. | |
| 824 */ | |
| 825 factory Uint64List(int length) { | |
| 826 throw new UnsupportedError("Uint64List not supported by dart2js."); | |
| 827 } | |
| 828 | |
| 829 /** | |
| 830 * Creates a [Uint64List] with the same size as the [elements] list | |
| 831 * and copies over the elements. | |
| 832 */ | |
| 833 factory Uint64List.fromList(List<int> list) { | |
| 834 throw new UnsupportedError("Uint64List not supported by dart2js."); | |
| 835 } | |
| 836 | |
| 837 /** | |
| 838 * Creates an [Uint64List] _view_ of the specified region in | |
| 839 * the specified byte buffer. Changes in the [Uint64List] will be | |
| 840 * visible in the byte buffer and vice versa. If the [offsetInBytes] | |
| 841 * index of the region is not specified, it defaults to zero (the first | |
| 842 * byte in the byte buffer). If the length is not specified, it defaults | |
| 843 * to null, which indicates that the view extends to the end of the byte | |
| 844 * buffer. | |
| 845 * | |
| 846 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 847 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 848 * the length of [buffer]. | |
| 849 * | |
| 850 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 851 * BYTES_PER_ELEMENT. | |
| 852 */ | |
| 853 factory Uint64List.view(ByteBuffer buffer, [int byteOffset, int length]) { | |
| 854 throw new UnsupportedError("Uint64List not supported by dart2js."); | |
| 855 } | |
| 856 | |
| 857 static const int BYTES_PER_ELEMENT = 8; | |
| 858 } | |
| 859 | |
| 860 | |
| 861 /** | |
| 862 * A fixed-length list of Float32x4 numbers that is viewable as a | |
| 863 * [TypedData]. For long lists, this implementation will be considerably more | |
| 864 * space- and time-efficient than the default [List] implementation. | |
| 865 */ | |
| 866 class Float32x4List | |
| 867 extends Object with ListMixin<Float32x4>, FixedLengthListMixin<Float32x4> | |
| 868 implements List<Float32x4>, TypedData { | |
| 869 | |
| 870 final Float32List _storage; | |
| 871 | |
| 872 ByteBuffer get buffer => _storage.buffer; | |
| 873 | |
| 874 int get lengthInBytes => _storage.lengthInBytes; | |
| 875 | |
| 876 int get offsetInBytes => _storage.offsetInBytes; | |
| 877 | |
| 878 int get elementSizeInBytes => BYTES_PER_ELEMENT; | |
| 879 | |
| 880 void _invalidIndex(int index, int length) { | |
| 881 if (index < 0 || index >= length) { | |
| 882 throw new RangeError.range(index, 0, length); | |
| 883 } else { | |
| 884 throw new ArgumentError('Invalid list index $index'); | |
| 885 } | |
| 886 } | |
| 887 | |
| 888 void _checkIndex(int index, int length) { | |
| 889 if (JS('bool', '(# >>> 0 != #)', index, index) || index >= length) { | |
| 890 _invalidIndex(index, length); | |
| 891 } | |
| 892 } | |
| 893 | |
| 894 int _checkSublistArguments(int start, int end, int length) { | |
| 895 // For `sublist` the [start] and [end] indices are allowed to be equal to | |
| 896 // [length]. However, [_checkIndex] only allows indices in the range | |
| 897 // 0 .. length - 1. We therefore increment the [length] argument by one | |
| 898 // for the [_checkIndex] checks. | |
| 899 _checkIndex(start, length + 1); | |
| 900 if (end == null) return length; | |
| 901 _checkIndex(end, length + 1); | |
| 902 if (start > end) throw new RangeError.range(start, 0, end); | |
| 903 return end; | |
| 904 } | |
| 905 | |
| 906 /** | |
| 907 * Creates a [Float32x4List] of the specified length (in elements), | |
| 908 * all of whose elements are initially zero. | |
| 909 */ | |
| 910 Float32x4List(int length) : _storage = new Float32List(length*4); | |
| 911 | |
| 912 Float32x4List._externalStorage(Float32List storage) : _storage = storage; | |
| 913 | |
| 914 Float32x4List._slowFromList(List<Float32x4> list) | |
| 915 : _storage = new Float32List(list.length * 4) { | |
| 916 for (int i = 0; i < list.length; i++) { | |
| 917 var e = list[i]; | |
| 918 _storage[(i * 4) + 0] = e.x; | |
| 919 _storage[(i * 4) + 1] = e.y; | |
| 920 _storage[(i * 4) + 2] = e.z; | |
| 921 _storage[(i * 4) + 3] = e.w; | |
| 922 } | |
| 923 } | |
| 924 | |
| 925 /** | |
| 926 * Creates a [Float32x4List] with the same size as the [elements] list | |
| 927 * and copies over the elements. | |
| 928 */ | |
| 929 factory Float32x4List.fromList(List<Float32x4> list) { | |
| 930 if (list is Float32x4List) { | |
| 931 Float32x4List nativeList = list as Float32x4List; | |
| 932 return new Float32x4List._externalStorage( | |
| 933 new Float32List.fromList(nativeList._storage)); | |
| 934 } else { | |
| 935 return new Float32x4List._slowFromList(list); | |
| 936 } | |
| 937 } | |
| 938 | |
| 939 /** | |
| 940 * Creates a [Float32x4List] _view_ of the specified region in the specified | |
| 941 * byte buffer. Changes in the [Float32x4List] will be visible in the byte | |
| 942 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 943 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 944 * If the length is not specified, it defaults to null, which indicates | |
| 945 * that the view extends to the end of the byte buffer. | |
| 946 * | |
| 947 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 948 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 949 * the length of [buffer]. | |
| 950 * | |
| 951 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 952 * BYTES_PER_ELEMENT. | |
| 953 */ | |
| 954 Float32x4List.view(ByteBuffer buffer, | |
| 955 [int byteOffset = 0, int length]) | |
| 956 : _storage = buffer.asFloat32List(byteOffset, | |
| 957 length != null ? length * 4 : null); | |
| 958 | |
| 959 static const int BYTES_PER_ELEMENT = 16; | |
| 960 | |
| 961 int get length => _storage.length ~/ 4; | |
| 962 | |
| 963 Float32x4 operator[](int index) { | |
| 964 _checkIndex(index, length); | |
| 965 double _x = _storage[(index * 4) + 0]; | |
| 966 double _y = _storage[(index * 4) + 1]; | |
| 967 double _z = _storage[(index * 4) + 2]; | |
| 968 double _w = _storage[(index * 4) + 3]; | |
| 969 return new Float32x4(_x, _y, _z, _w); | |
| 970 } | |
| 971 | |
| 972 void operator[]=(int index, Float32x4 value) { | |
| 973 _checkIndex(index, length); | |
| 974 _storage[(index * 4) + 0] = value._storage[0]; | |
| 975 _storage[(index * 4) + 1] = value._storage[1]; | |
| 976 _storage[(index * 4) + 2] = value._storage[2]; | |
| 977 _storage[(index * 4) + 3] = value._storage[3]; | |
| 978 } | |
| 979 | |
| 980 List<Float32x4> sublist(int start, [int end]) { | |
| 981 end = _checkSublistArguments(start, end, length); | |
| 982 return new Float32x4List._externalStorage( | |
| 983 _storage.sublist(start * 4, end * 4)); | |
| 984 } | |
| 985 } | |
| 986 | |
| 987 | |
| 988 /** | |
| 989 * A fixed-length list of Int32x4 numbers that is viewable as a | |
| 990 * [TypedData]. For long lists, this implementation will be considerably more | |
| 991 * space- and time-efficient than the default [List] implementation. | |
| 992 */ | |
| 993 class Int32x4List | |
| 994 extends Object with ListMixin<Int32x4>, FixedLengthListMixin<Int32x4> | |
| 995 implements List<Int32x4>, TypedData { | |
| 996 | |
| 997 final Uint32List _storage; | |
| 998 | |
| 999 ByteBuffer get buffer => _storage.buffer; | |
| 1000 | |
| 1001 int get lengthInBytes => _storage.lengthInBytes; | |
| 1002 | |
| 1003 int get offsetInBytes => _storage.offsetInBytes; | |
| 1004 | |
| 1005 int get elementSizeInBytes => BYTES_PER_ELEMENT; | |
| 1006 | |
| 1007 void _invalidIndex(int index, int length) { | |
| 1008 if (index < 0 || index >= length) { | |
| 1009 throw new RangeError.range(index, 0, length); | |
| 1010 } else { | |
| 1011 throw new ArgumentError('Invalid list index $index'); | |
| 1012 } | |
| 1013 } | |
| 1014 | |
| 1015 void _checkIndex(int index, int length) { | |
| 1016 if (JS('bool', '(# >>> 0 != #)', index, index) | |
| 1017 || JS('bool', '# >= #', index, length)) { | |
| 1018 _invalidIndex(index, length); | |
| 1019 } | |
| 1020 } | |
| 1021 | |
| 1022 int _checkSublistArguments(int start, int end, int length) { | |
| 1023 // For `sublist` the [start] and [end] indices are allowed to be equal to | |
| 1024 // [length]. However, [_checkIndex] only allows indices in the range | |
| 1025 // 0 .. length - 1. We therefore increment the [length] argument by one | |
| 1026 // for the [_checkIndex] checks. | |
| 1027 _checkIndex(start, length + 1); | |
| 1028 if (end == null) return length; | |
| 1029 _checkIndex(end, length + 1); | |
| 1030 if (start > end) throw new RangeError.range(start, 0, end); | |
| 1031 return end; | |
| 1032 } | |
| 1033 | |
| 1034 /** | |
| 1035 * Creates a [Int32x4List] of the specified length (in elements), | |
| 1036 * all of whose elements are initially zero. | |
| 1037 */ | |
| 1038 Int32x4List(int length) : _storage = new Uint32List(length * 4); | |
| 1039 | |
| 1040 Int32x4List._externalStorage(Uint32List storage) : _storage = storage; | |
| 1041 | |
| 1042 Int32x4List._slowFromList(List<Int32x4> list) | |
| 1043 : _storage = new Uint32List(list.length * 4) { | |
| 1044 for (int i = 0; i < list.length; i++) { | |
| 1045 var e = list[i]; | |
| 1046 _storage[(i * 4) + 0] = e.x; | |
| 1047 _storage[(i * 4) + 1] = e.y; | |
| 1048 _storage[(i * 4) + 2] = e.z; | |
| 1049 _storage[(i * 4) + 3] = e.w; | |
| 1050 } | |
| 1051 } | |
| 1052 | |
| 1053 /** | |
| 1054 * Creates a [Int32x4List] with the same size as the [elements] list | |
| 1055 * and copies over the elements. | |
| 1056 */ | |
| 1057 factory Int32x4List.fromList(List<Int32x4> list) { | |
| 1058 if (list is Int32x4List) { | |
| 1059 return new Int32x4List._externalStorage( | |
| 1060 new Uint32List.fromList(list._storage)); | |
| 1061 } else { | |
| 1062 return new Int32x4List._slowFromList(list); | |
| 1063 } | |
| 1064 } | |
| 1065 | |
| 1066 /** | |
| 1067 * Creates a [Int32x4List] _view_ of the specified region in the specified | |
| 1068 * byte buffer. Changes in the [Int32x4List] will be visible in the byte | |
| 1069 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 1070 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 1071 * If the length is not specified, it defaults to null, which indicates | |
| 1072 * that the view extends to the end of the byte buffer. | |
| 1073 * | |
| 1074 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 1075 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 1076 * the length of [buffer]. | |
| 1077 * | |
| 1078 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 1079 * BYTES_PER_ELEMENT. | |
| 1080 */ | |
| 1081 Int32x4List.view(ByteBuffer buffer, | |
| 1082 [int byteOffset = 0, int length]) | |
| 1083 : _storage = buffer.asUint32List(byteOffset, | |
| 1084 length != null ? length * 4 : null); | |
| 1085 | |
| 1086 static const int BYTES_PER_ELEMENT = 16; | |
| 1087 | |
| 1088 int get length => _storage.length ~/ 4; | |
| 1089 | |
| 1090 Int32x4 operator[](int index) { | |
| 1091 _checkIndex(index, length); | |
| 1092 int _x = _storage[(index * 4) + 0]; | |
| 1093 int _y = _storage[(index * 4) + 1]; | |
| 1094 int _z = _storage[(index * 4) + 2]; | |
| 1095 int _w = _storage[(index * 4) + 3]; | |
| 1096 return new Int32x4(_x, _y, _z, _w); | |
| 1097 } | |
| 1098 | |
| 1099 void operator[]=(int index, Int32x4 value) { | |
| 1100 _checkIndex(index, length); | |
| 1101 _storage[(index * 4) + 0] = value._storage[0]; | |
| 1102 _storage[(index * 4) + 1] = value._storage[1]; | |
| 1103 _storage[(index * 4) + 2] = value._storage[2]; | |
| 1104 _storage[(index * 4) + 3] = value._storage[3]; | |
| 1105 } | |
| 1106 | |
| 1107 List<Int32x4> sublist(int start, [int end]) { | |
| 1108 end = _checkSublistArguments(start, end, length); | |
| 1109 return new Int32x4List._externalStorage(_storage.sublist(start*4, end*4)); | |
| 1110 } | |
| 1111 } | |
| 1112 | |
| 1113 | |
| 1114 /** | |
| 1115 * A fixed-length list of Float64x2 numbers that is viewable as a | |
| 1116 * [TypedData]. For long lists, this implementation will be considerably more | |
| 1117 * space- and time-efficient than the default [List] implementation. | |
| 1118 */ | |
| 1119 class Float64x2List | |
| 1120 extends Object with ListMixin<Float64x2>, FixedLengthListMixin<Float64x2> | |
| 1121 implements List<Float64x2>, TypedData { | |
| 1122 | |
| 1123 final Float64List _storage; | |
| 1124 | |
| 1125 ByteBuffer get buffer => _storage.buffer; | |
| 1126 | |
| 1127 int get lengthInBytes => _storage.lengthInBytes; | |
| 1128 | |
| 1129 int get offsetInBytes => _storage.offsetInBytes; | |
| 1130 | |
| 1131 int get elementSizeInBytes => BYTES_PER_ELEMENT; | |
| 1132 | |
| 1133 void _invalidIndex(int index, int length) { | |
| 1134 if (index < 0 || index >= length) { | |
| 1135 throw new RangeError.range(index, 0, length); | |
| 1136 } else { | |
| 1137 throw new ArgumentError('Invalid list index $index'); | |
| 1138 } | |
| 1139 } | |
| 1140 | |
| 1141 void _checkIndex(int index, int length) { | |
| 1142 if (JS('bool', '(# >>> 0 != #)', index, index) || index >= length) { | |
| 1143 _invalidIndex(index, length); | |
| 1144 } | |
| 1145 } | |
| 1146 | |
| 1147 int _checkSublistArguments(int start, int end, int length) { | |
| 1148 // For `sublist` the [start] and [end] indices are allowed to be equal to | |
| 1149 // [length]. However, [_checkIndex] only allows indices in the range | |
| 1150 // 0 .. length - 1. We therefore increment the [length] argument by one | |
| 1151 // for the [_checkIndex] checks. | |
| 1152 _checkIndex(start, length + 1); | |
| 1153 if (end == null) return length; | |
| 1154 _checkIndex(end, length + 1); | |
| 1155 if (start > end) throw new RangeError.range(start, 0, end); | |
| 1156 return end; | |
| 1157 } | |
| 1158 | |
| 1159 /** | |
| 1160 * Creates a [Float64x2List] of the specified length (in elements), | |
| 1161 * all of whose elements are initially zero. | |
| 1162 */ | |
| 1163 Float64x2List(int length) : _storage = new Float64List(length * 2); | |
| 1164 | |
| 1165 Float64x2List._externalStorage(Float64List storage) : _storage = storage; | |
| 1166 | |
| 1167 Float64x2List._slowFromList(List<Float64x2> list) | |
| 1168 : _storage = new Float64List(list.length * 2) { | |
| 1169 for (int i = 0; i < list.length; i++) { | |
| 1170 var e = list[i]; | |
| 1171 _storage[(i * 2) + 0] = e.x; | |
| 1172 _storage[(i * 2) + 1] = e.y; | |
| 1173 } | |
| 1174 } | |
| 1175 | |
| 1176 /** | |
| 1177 * Creates a [Float64x2List] with the same size as the [elements] list | |
| 1178 * and copies over the elements. | |
| 1179 */ | |
| 1180 factory Float64x2List.fromList(List<Float64x2> list) { | |
| 1181 if (list is Float64x2List) { | |
| 1182 Float64x2List nativeList = list as Float64x2List; | |
| 1183 return new Float64x2List._externalStorage( | |
| 1184 new Float64List.fromList(nativeList._storage)); | |
| 1185 } else { | |
| 1186 return new Float64x2List._slowFromList(list); | |
| 1187 } | |
| 1188 } | |
| 1189 | |
| 1190 /** | |
| 1191 * Creates a [Float64x2List] _view_ of the specified region in the specified | |
| 1192 * byte buffer. Changes in the [Float64x2List] will be visible in the byte | |
| 1193 * buffer and vice versa. If the [offsetInBytes] index of the region is not | |
| 1194 * specified, it defaults to zero (the first byte in the byte buffer). | |
| 1195 * If the length is not specified, it defaults to null, which indicates | |
| 1196 * that the view extends to the end of the byte buffer. | |
| 1197 * | |
| 1198 * Throws [RangeError] if [offsetInBytes] or [length] are negative, or | |
| 1199 * if [offsetInBytes] + ([length] * elementSizeInBytes) is greater than | |
| 1200 * the length of [buffer]. | |
| 1201 * | |
| 1202 * Throws [ArgumentError] if [offsetInBytes] is not a multiple of | |
| 1203 * BYTES_PER_ELEMENT. | |
| 1204 */ | |
| 1205 Float64x2List.view(ByteBuffer buffer, | |
| 1206 [int byteOffset = 0, int length]) | |
| 1207 : _storage = buffer.asFloat64List(byteOffset, | |
| 1208 length != null ? length * 2 : null); | |
| 1209 | |
| 1210 static const int BYTES_PER_ELEMENT = 16; | |
| 1211 | |
| 1212 int get length => _storage.length ~/ 2; | |
| 1213 | |
| 1214 Float64x2 operator[](int index) { | |
| 1215 _checkIndex(index, length); | |
| 1216 double _x = _storage[(index * 2) + 0]; | |
| 1217 double _y = _storage[(index * 2) + 1]; | |
| 1218 return new Float64x2(_x, _y); | |
| 1219 } | |
| 1220 | |
| 1221 void operator[]=(int index, Float64x2 value) { | |
| 1222 _checkIndex(index, length); | |
| 1223 _storage[(index * 2) + 0] = value._storage[0]; | |
| 1224 _storage[(index * 2) + 1] = value._storage[1]; | |
| 1225 } | |
| 1226 | |
| 1227 List<Float64x2> sublist(int start, [int end]) { | |
| 1228 end = _checkSublistArguments(start, end, length); | |
| 1229 return new Float64x2List._externalStorage( | |
| 1230 _storage.sublist(start * 2, end * 2)); | |
| 1231 } | |
| 1232 } | |
| 1233 | |
| 1234 | |
| 1235 /** | |
| 1236 * Interface of Dart Float32x4 immutable value type and operations. | |
| 1237 * Float32x4 stores 4 32-bit floating point values in "lanes". | |
| 1238 * The lanes are "x", "y", "z", and "w" respectively. | |
| 1239 */ | |
| 1240 class Float32x4 { | |
| 1241 final _storage = new Float32List(4); | |
| 1242 | |
| 1243 Float32x4(double x, double y, double z, double w) { | |
| 1244 _storage[0] = x; | |
| 1245 _storage[1] = y; | |
| 1246 _storage[2] = z; | |
| 1247 _storage[3] = w; | |
| 1248 } | |
| 1249 Float32x4.splat(double v) { | |
| 1250 _storage[0] = v; | |
| 1251 _storage[1] = v; | |
| 1252 _storage[2] = v; | |
| 1253 _storage[3] = v; | |
| 1254 } | |
| 1255 Float32x4.zero(); | |
| 1256 /// Returns a bit-wise copy of [x] as a Float32x4. | |
| 1257 Float32x4.fromInt32x4Bits(Int32x4 x) { | |
| 1258 var view = new Float32List.view(x._storage.buffer); | |
| 1259 _storage[0] = view[0]; | |
| 1260 _storage[1] = view[1]; | |
| 1261 _storage[2] = view[2]; | |
| 1262 _storage[3] = view[3]; | |
| 1263 } | |
| 1264 Float32x4.fromFloat64x2(Float64x2 v) { | |
| 1265 _storage[0] = v._storage[0]; | |
| 1266 _storage[1] = v._storage[1]; | |
| 1267 } | |
| 1268 | |
| 1269 String toString() { | |
| 1270 return '[${_storage[0]}, ${_storage[1]}, ${_storage[2]}, ${_storage[3]}]'; | |
| 1271 } | |
| 1272 | |
| 1273 /// Addition operator. | |
| 1274 Float32x4 operator+(Float32x4 other) { | |
| 1275 double _x = _storage[0] + other._storage[0]; | |
| 1276 double _y = _storage[1] + other._storage[1]; | |
| 1277 double _z = _storage[2] + other._storage[2]; | |
| 1278 double _w = _storage[3] + other._storage[3]; | |
| 1279 return new Float32x4(_x, _y, _z, _w); | |
| 1280 } | |
| 1281 | |
| 1282 /// Negate operator. | |
| 1283 Float32x4 operator-() { | |
| 1284 double _x = -_storage[0]; | |
| 1285 double _y = -_storage[1]; | |
| 1286 double _z = -_storage[2]; | |
| 1287 double _w = -_storage[3]; | |
| 1288 return new Float32x4(_x, _y, _z, _w); | |
| 1289 } | |
| 1290 | |
| 1291 /// Subtraction operator. | |
| 1292 Float32x4 operator-(Float32x4 other) { | |
| 1293 double _x = _storage[0] - other._storage[0]; | |
| 1294 double _y = _storage[1] - other._storage[1]; | |
| 1295 double _z = _storage[2] - other._storage[2]; | |
| 1296 double _w = _storage[3] - other._storage[3]; | |
| 1297 return new Float32x4(_x, _y, _z, _w); | |
| 1298 } | |
| 1299 | |
| 1300 /// Multiplication operator. | |
| 1301 Float32x4 operator*(Float32x4 other) { | |
| 1302 double _x = _storage[0] * other._storage[0]; | |
| 1303 double _y = _storage[1] * other._storage[1]; | |
| 1304 double _z = _storage[2] * other._storage[2]; | |
| 1305 double _w = _storage[3] * other._storage[3]; | |
| 1306 return new Float32x4(_x, _y, _z, _w); | |
| 1307 } | |
| 1308 | |
| 1309 /// Division operator. | |
| 1310 Float32x4 operator/(Float32x4 other) { | |
| 1311 double _x = _storage[0] / other._storage[0]; | |
| 1312 double _y = _storage[1] / other._storage[1]; | |
| 1313 double _z = _storage[2] / other._storage[2]; | |
| 1314 double _w = _storage[3] / other._storage[3]; | |
| 1315 return new Float32x4(_x, _y, _z, _w); | |
| 1316 } | |
| 1317 | |
| 1318 /// Relational less than. | |
| 1319 Int32x4 lessThan(Float32x4 other) { | |
| 1320 bool _cx = _storage[0] < other._storage[0]; | |
| 1321 bool _cy = _storage[1] < other._storage[1]; | |
| 1322 bool _cz = _storage[2] < other._storage[2]; | |
| 1323 bool _cw = _storage[3] < other._storage[3]; | |
| 1324 return new Int32x4(_cx == true ? 0xFFFFFFFF : 0x0, | |
| 1325 _cy == true ? 0xFFFFFFFF : 0x0, | |
| 1326 _cz == true ? 0xFFFFFFFF : 0x0, | |
| 1327 _cw == true ? 0xFFFFFFFF : 0x0); | |
| 1328 } | |
| 1329 | |
| 1330 /// Relational less than or equal. | |
| 1331 Int32x4 lessThanOrEqual(Float32x4 other) { | |
| 1332 bool _cx = _storage[0] <= other._storage[0]; | |
| 1333 bool _cy = _storage[1] <= other._storage[1]; | |
| 1334 bool _cz = _storage[2] <= other._storage[2]; | |
| 1335 bool _cw = _storage[3] <= other._storage[3]; | |
| 1336 return new Int32x4(_cx == true ? 0xFFFFFFFF : 0x0, | |
| 1337 _cy == true ? 0xFFFFFFFF : 0x0, | |
| 1338 _cz == true ? 0xFFFFFFFF : 0x0, | |
| 1339 _cw == true ? 0xFFFFFFFF : 0x0); | |
| 1340 } | |
| 1341 | |
| 1342 /// Relational greater than. | |
| 1343 Int32x4 greaterThan(Float32x4 other) { | |
| 1344 bool _cx = _storage[0] > other._storage[0]; | |
| 1345 bool _cy = _storage[1] > other._storage[1]; | |
| 1346 bool _cz = _storage[2] > other._storage[2]; | |
| 1347 bool _cw = _storage[3] > other._storage[3]; | |
| 1348 return new Int32x4(_cx == true ? 0xFFFFFFFF : 0x0, | |
| 1349 _cy == true ? 0xFFFFFFFF : 0x0, | |
| 1350 _cz == true ? 0xFFFFFFFF : 0x0, | |
| 1351 _cw == true ? 0xFFFFFFFF : 0x0); | |
| 1352 } | |
| 1353 | |
| 1354 /// Relational greater than or equal. | |
| 1355 Int32x4 greaterThanOrEqual(Float32x4 other) { | |
| 1356 bool _cx = _storage[0] >= other._storage[0]; | |
| 1357 bool _cy = _storage[1] >= other._storage[1]; | |
| 1358 bool _cz = _storage[2] >= other._storage[2]; | |
| 1359 bool _cw = _storage[3] >= other._storage[3]; | |
| 1360 return new Int32x4(_cx == true ? 0xFFFFFFFF : 0x0, | |
| 1361 _cy == true ? 0xFFFFFFFF : 0x0, | |
| 1362 _cz == true ? 0xFFFFFFFF : 0x0, | |
| 1363 _cw == true ? 0xFFFFFFFF : 0x0); | |
| 1364 } | |
| 1365 | |
| 1366 /// Relational equal. | |
| 1367 Int32x4 equal(Float32x4 other) { | |
| 1368 bool _cx = _storage[0] == other._storage[0]; | |
| 1369 bool _cy = _storage[1] == other._storage[1]; | |
| 1370 bool _cz = _storage[2] == other._storage[2]; | |
| 1371 bool _cw = _storage[3] == other._storage[3]; | |
| 1372 return new Int32x4(_cx == true ? 0xFFFFFFFF : 0x0, | |
| 1373 _cy == true ? 0xFFFFFFFF : 0x0, | |
| 1374 _cz == true ? 0xFFFFFFFF : 0x0, | |
| 1375 _cw == true ? 0xFFFFFFFF : 0x0); | |
| 1376 } | |
| 1377 | |
| 1378 /// Relational not-equal. | |
| 1379 Int32x4 notEqual(Float32x4 other) { | |
| 1380 bool _cx = _storage[0] != other._storage[0]; | |
| 1381 bool _cy = _storage[1] != other._storage[1]; | |
| 1382 bool _cz = _storage[2] != other._storage[2]; | |
| 1383 bool _cw = _storage[3] != other._storage[3]; | |
| 1384 return new Int32x4(_cx == true ? 0xFFFFFFFF : 0x0, | |
| 1385 _cy == true ? 0xFFFFFFFF : 0x0, | |
| 1386 _cz == true ? 0xFFFFFFFF : 0x0, | |
| 1387 _cw == true ? 0xFFFFFFFF : 0x0); | |
| 1388 } | |
| 1389 | |
| 1390 /// Returns a copy of [this] each lane being scaled by [s]. | |
| 1391 Float32x4 scale(double s) { | |
| 1392 double _x = s * _storage[0]; | |
| 1393 double _y = s * _storage[1]; | |
| 1394 double _z = s * _storage[2]; | |
| 1395 double _w = s * _storage[3]; | |
| 1396 return new Float32x4(_x, _y, _z, _w); | |
| 1397 } | |
| 1398 | |
| 1399 /// Returns the absolute value of this [Float32x4]. | |
| 1400 Float32x4 abs() { | |
| 1401 double _x = _storage[0].abs(); | |
| 1402 double _y = _storage[1].abs(); | |
| 1403 double _z = _storage[2].abs(); | |
| 1404 double _w = _storage[3].abs(); | |
| 1405 return new Float32x4(_x, _y, _z, _w); | |
| 1406 } | |
| 1407 | |
| 1408 /// Clamps [this] to be in the range [lowerLimit]-[upperLimit]. | |
| 1409 Float32x4 clamp(Float32x4 lowerLimit, Float32x4 upperLimit) { | |
| 1410 double _lx = lowerLimit._storage[0]; | |
| 1411 double _ly = lowerLimit._storage[1]; | |
| 1412 double _lz = lowerLimit._storage[2]; | |
| 1413 double _lw = lowerLimit._storage[3]; | |
| 1414 double _ux = upperLimit._storage[0]; | |
| 1415 double _uy = upperLimit._storage[1]; | |
| 1416 double _uz = upperLimit._storage[2]; | |
| 1417 double _uw = upperLimit._storage[3]; | |
| 1418 double _x = _storage[0]; | |
| 1419 double _y = _storage[1]; | |
| 1420 double _z = _storage[2]; | |
| 1421 double _w = _storage[3]; | |
| 1422 // MAX(MIN(self, upper), lower). | |
| 1423 _x = _x > _ux ? _ux : _x; | |
| 1424 _y = _y > _uy ? _uy : _y; | |
| 1425 _z = _z > _uz ? _uz : _z; | |
| 1426 _w = _w > _uw ? _uw : _w; | |
| 1427 _x = _x < _lx ? _lx : _x; | |
| 1428 _y = _y < _ly ? _ly : _y; | |
| 1429 _z = _z < _lz ? _lz : _z; | |
| 1430 _w = _w < _lw ? _lw : _w; | |
| 1431 return new Float32x4(_x, _y, _z, _w); | |
| 1432 } | |
| 1433 | |
| 1434 /// Extracted x value. | |
| 1435 double get x => _storage[0]; | |
| 1436 /// Extracted y value. | |
| 1437 double get y => _storage[1]; | |
| 1438 /// Extracted z value. | |
| 1439 double get z => _storage[2]; | |
| 1440 /// Extracted w value. | |
| 1441 double get w => _storage[3]; | |
| 1442 | |
| 1443 /// Extract the sign bit from each lane return them in the first 4 bits. | |
| 1444 int get signMask { | |
| 1445 var view = new Uint32List.view(_storage.buffer); | |
| 1446 var mx = (view[0] & 0x80000000) >> 31; | |
| 1447 var my = (view[1] & 0x80000000) >> 31; | |
| 1448 var mz = (view[2] & 0x80000000) >> 31; | |
| 1449 var mw = (view[3] & 0x80000000) >> 31; | |
| 1450 return mx | my << 1 | mz << 2 | mw << 3; | |
| 1451 } | |
| 1452 | |
| 1453 /// Mask passed to [shuffle] and [shuffleMix]. | |
| 1454 static const int XXXX = 0x0; | |
| 1455 static const int XXXY = 0x40; | |
| 1456 static const int XXXZ = 0x80; | |
| 1457 static const int XXXW = 0xC0; | |
| 1458 static const int XXYX = 0x10; | |
| 1459 static const int XXYY = 0x50; | |
| 1460 static const int XXYZ = 0x90; | |
| 1461 static const int XXYW = 0xD0; | |
| 1462 static const int XXZX = 0x20; | |
| 1463 static const int XXZY = 0x60; | |
| 1464 static const int XXZZ = 0xA0; | |
| 1465 static const int XXZW = 0xE0; | |
| 1466 static const int XXWX = 0x30; | |
| 1467 static const int XXWY = 0x70; | |
| 1468 static const int XXWZ = 0xB0; | |
| 1469 static const int XXWW = 0xF0; | |
| 1470 static const int XYXX = 0x4; | |
| 1471 static const int XYXY = 0x44; | |
| 1472 static const int XYXZ = 0x84; | |
| 1473 static const int XYXW = 0xC4; | |
| 1474 static const int XYYX = 0x14; | |
| 1475 static const int XYYY = 0x54; | |
| 1476 static const int XYYZ = 0x94; | |
| 1477 static const int XYYW = 0xD4; | |
| 1478 static const int XYZX = 0x24; | |
| 1479 static const int XYZY = 0x64; | |
| 1480 static const int XYZZ = 0xA4; | |
| 1481 static const int XYZW = 0xE4; | |
| 1482 static const int XYWX = 0x34; | |
| 1483 static const int XYWY = 0x74; | |
| 1484 static const int XYWZ = 0xB4; | |
| 1485 static const int XYWW = 0xF4; | |
| 1486 static const int XZXX = 0x8; | |
| 1487 static const int XZXY = 0x48; | |
| 1488 static const int XZXZ = 0x88; | |
| 1489 static const int XZXW = 0xC8; | |
| 1490 static const int XZYX = 0x18; | |
| 1491 static const int XZYY = 0x58; | |
| 1492 static const int XZYZ = 0x98; | |
| 1493 static const int XZYW = 0xD8; | |
| 1494 static const int XZZX = 0x28; | |
| 1495 static const int XZZY = 0x68; | |
| 1496 static const int XZZZ = 0xA8; | |
| 1497 static const int XZZW = 0xE8; | |
| 1498 static const int XZWX = 0x38; | |
| 1499 static const int XZWY = 0x78; | |
| 1500 static const int XZWZ = 0xB8; | |
| 1501 static const int XZWW = 0xF8; | |
| 1502 static const int XWXX = 0xC; | |
| 1503 static const int XWXY = 0x4C; | |
| 1504 static const int XWXZ = 0x8C; | |
| 1505 static const int XWXW = 0xCC; | |
| 1506 static const int XWYX = 0x1C; | |
| 1507 static const int XWYY = 0x5C; | |
| 1508 static const int XWYZ = 0x9C; | |
| 1509 static const int XWYW = 0xDC; | |
| 1510 static const int XWZX = 0x2C; | |
| 1511 static const int XWZY = 0x6C; | |
| 1512 static const int XWZZ = 0xAC; | |
| 1513 static const int XWZW = 0xEC; | |
| 1514 static const int XWWX = 0x3C; | |
| 1515 static const int XWWY = 0x7C; | |
| 1516 static const int XWWZ = 0xBC; | |
| 1517 static const int XWWW = 0xFC; | |
| 1518 static const int YXXX = 0x1; | |
| 1519 static const int YXXY = 0x41; | |
| 1520 static const int YXXZ = 0x81; | |
| 1521 static const int YXXW = 0xC1; | |
| 1522 static const int YXYX = 0x11; | |
| 1523 static const int YXYY = 0x51; | |
| 1524 static const int YXYZ = 0x91; | |
| 1525 static const int YXYW = 0xD1; | |
| 1526 static const int YXZX = 0x21; | |
| 1527 static const int YXZY = 0x61; | |
| 1528 static const int YXZZ = 0xA1; | |
| 1529 static const int YXZW = 0xE1; | |
| 1530 static const int YXWX = 0x31; | |
| 1531 static const int YXWY = 0x71; | |
| 1532 static const int YXWZ = 0xB1; | |
| 1533 static const int YXWW = 0xF1; | |
| 1534 static const int YYXX = 0x5; | |
| 1535 static const int YYXY = 0x45; | |
| 1536 static const int YYXZ = 0x85; | |
| 1537 static const int YYXW = 0xC5; | |
| 1538 static const int YYYX = 0x15; | |
| 1539 static const int YYYY = 0x55; | |
| 1540 static const int YYYZ = 0x95; | |
| 1541 static const int YYYW = 0xD5; | |
| 1542 static const int YYZX = 0x25; | |
| 1543 static const int YYZY = 0x65; | |
| 1544 static const int YYZZ = 0xA5; | |
| 1545 static const int YYZW = 0xE5; | |
| 1546 static const int YYWX = 0x35; | |
| 1547 static const int YYWY = 0x75; | |
| 1548 static const int YYWZ = 0xB5; | |
| 1549 static const int YYWW = 0xF5; | |
| 1550 static const int YZXX = 0x9; | |
| 1551 static const int YZXY = 0x49; | |
| 1552 static const int YZXZ = 0x89; | |
| 1553 static const int YZXW = 0xC9; | |
| 1554 static const int YZYX = 0x19; | |
| 1555 static const int YZYY = 0x59; | |
| 1556 static const int YZYZ = 0x99; | |
| 1557 static const int YZYW = 0xD9; | |
| 1558 static const int YZZX = 0x29; | |
| 1559 static const int YZZY = 0x69; | |
| 1560 static const int YZZZ = 0xA9; | |
| 1561 static const int YZZW = 0xE9; | |
| 1562 static const int YZWX = 0x39; | |
| 1563 static const int YZWY = 0x79; | |
| 1564 static const int YZWZ = 0xB9; | |
| 1565 static const int YZWW = 0xF9; | |
| 1566 static const int YWXX = 0xD; | |
| 1567 static const int YWXY = 0x4D; | |
| 1568 static const int YWXZ = 0x8D; | |
| 1569 static const int YWXW = 0xCD; | |
| 1570 static const int YWYX = 0x1D; | |
| 1571 static const int YWYY = 0x5D; | |
| 1572 static const int YWYZ = 0x9D; | |
| 1573 static const int YWYW = 0xDD; | |
| 1574 static const int YWZX = 0x2D; | |
| 1575 static const int YWZY = 0x6D; | |
| 1576 static const int YWZZ = 0xAD; | |
| 1577 static const int YWZW = 0xED; | |
| 1578 static const int YWWX = 0x3D; | |
| 1579 static const int YWWY = 0x7D; | |
| 1580 static const int YWWZ = 0xBD; | |
| 1581 static const int YWWW = 0xFD; | |
| 1582 static const int ZXXX = 0x2; | |
| 1583 static const int ZXXY = 0x42; | |
| 1584 static const int ZXXZ = 0x82; | |
| 1585 static const int ZXXW = 0xC2; | |
| 1586 static const int ZXYX = 0x12; | |
| 1587 static const int ZXYY = 0x52; | |
| 1588 static const int ZXYZ = 0x92; | |
| 1589 static const int ZXYW = 0xD2; | |
| 1590 static const int ZXZX = 0x22; | |
| 1591 static const int ZXZY = 0x62; | |
| 1592 static const int ZXZZ = 0xA2; | |
| 1593 static const int ZXZW = 0xE2; | |
| 1594 static const int ZXWX = 0x32; | |
| 1595 static const int ZXWY = 0x72; | |
| 1596 static const int ZXWZ = 0xB2; | |
| 1597 static const int ZXWW = 0xF2; | |
| 1598 static const int ZYXX = 0x6; | |
| 1599 static const int ZYXY = 0x46; | |
| 1600 static const int ZYXZ = 0x86; | |
| 1601 static const int ZYXW = 0xC6; | |
| 1602 static const int ZYYX = 0x16; | |
| 1603 static const int ZYYY = 0x56; | |
| 1604 static const int ZYYZ = 0x96; | |
| 1605 static const int ZYYW = 0xD6; | |
| 1606 static const int ZYZX = 0x26; | |
| 1607 static const int ZYZY = 0x66; | |
| 1608 static const int ZYZZ = 0xA6; | |
| 1609 static const int ZYZW = 0xE6; | |
| 1610 static const int ZYWX = 0x36; | |
| 1611 static const int ZYWY = 0x76; | |
| 1612 static const int ZYWZ = 0xB6; | |
| 1613 static const int ZYWW = 0xF6; | |
| 1614 static const int ZZXX = 0xA; | |
| 1615 static const int ZZXY = 0x4A; | |
| 1616 static const int ZZXZ = 0x8A; | |
| 1617 static const int ZZXW = 0xCA; | |
| 1618 static const int ZZYX = 0x1A; | |
| 1619 static const int ZZYY = 0x5A; | |
| 1620 static const int ZZYZ = 0x9A; | |
| 1621 static const int ZZYW = 0xDA; | |
| 1622 static const int ZZZX = 0x2A; | |
| 1623 static const int ZZZY = 0x6A; | |
| 1624 static const int ZZZZ = 0xAA; | |
| 1625 static const int ZZZW = 0xEA; | |
| 1626 static const int ZZWX = 0x3A; | |
| 1627 static const int ZZWY = 0x7A; | |
| 1628 static const int ZZWZ = 0xBA; | |
| 1629 static const int ZZWW = 0xFA; | |
| 1630 static const int ZWXX = 0xE; | |
| 1631 static const int ZWXY = 0x4E; | |
| 1632 static const int ZWXZ = 0x8E; | |
| 1633 static const int ZWXW = 0xCE; | |
| 1634 static const int ZWYX = 0x1E; | |
| 1635 static const int ZWYY = 0x5E; | |
| 1636 static const int ZWYZ = 0x9E; | |
| 1637 static const int ZWYW = 0xDE; | |
| 1638 static const int ZWZX = 0x2E; | |
| 1639 static const int ZWZY = 0x6E; | |
| 1640 static const int ZWZZ = 0xAE; | |
| 1641 static const int ZWZW = 0xEE; | |
| 1642 static const int ZWWX = 0x3E; | |
| 1643 static const int ZWWY = 0x7E; | |
| 1644 static const int ZWWZ = 0xBE; | |
| 1645 static const int ZWWW = 0xFE; | |
| 1646 static const int WXXX = 0x3; | |
| 1647 static const int WXXY = 0x43; | |
| 1648 static const int WXXZ = 0x83; | |
| 1649 static const int WXXW = 0xC3; | |
| 1650 static const int WXYX = 0x13; | |
| 1651 static const int WXYY = 0x53; | |
| 1652 static const int WXYZ = 0x93; | |
| 1653 static const int WXYW = 0xD3; | |
| 1654 static const int WXZX = 0x23; | |
| 1655 static const int WXZY = 0x63; | |
| 1656 static const int WXZZ = 0xA3; | |
| 1657 static const int WXZW = 0xE3; | |
| 1658 static const int WXWX = 0x33; | |
| 1659 static const int WXWY = 0x73; | |
| 1660 static const int WXWZ = 0xB3; | |
| 1661 static const int WXWW = 0xF3; | |
| 1662 static const int WYXX = 0x7; | |
| 1663 static const int WYXY = 0x47; | |
| 1664 static const int WYXZ = 0x87; | |
| 1665 static const int WYXW = 0xC7; | |
| 1666 static const int WYYX = 0x17; | |
| 1667 static const int WYYY = 0x57; | |
| 1668 static const int WYYZ = 0x97; | |
| 1669 static const int WYYW = 0xD7; | |
| 1670 static const int WYZX = 0x27; | |
| 1671 static const int WYZY = 0x67; | |
| 1672 static const int WYZZ = 0xA7; | |
| 1673 static const int WYZW = 0xE7; | |
| 1674 static const int WYWX = 0x37; | |
| 1675 static const int WYWY = 0x77; | |
| 1676 static const int WYWZ = 0xB7; | |
| 1677 static const int WYWW = 0xF7; | |
| 1678 static const int WZXX = 0xB; | |
| 1679 static const int WZXY = 0x4B; | |
| 1680 static const int WZXZ = 0x8B; | |
| 1681 static const int WZXW = 0xCB; | |
| 1682 static const int WZYX = 0x1B; | |
| 1683 static const int WZYY = 0x5B; | |
| 1684 static const int WZYZ = 0x9B; | |
| 1685 static const int WZYW = 0xDB; | |
| 1686 static const int WZZX = 0x2B; | |
| 1687 static const int WZZY = 0x6B; | |
| 1688 static const int WZZZ = 0xAB; | |
| 1689 static const int WZZW = 0xEB; | |
| 1690 static const int WZWX = 0x3B; | |
| 1691 static const int WZWY = 0x7B; | |
| 1692 static const int WZWZ = 0xBB; | |
| 1693 static const int WZWW = 0xFB; | |
| 1694 static const int WWXX = 0xF; | |
| 1695 static const int WWXY = 0x4F; | |
| 1696 static const int WWXZ = 0x8F; | |
| 1697 static const int WWXW = 0xCF; | |
| 1698 static const int WWYX = 0x1F; | |
| 1699 static const int WWYY = 0x5F; | |
| 1700 static const int WWYZ = 0x9F; | |
| 1701 static const int WWYW = 0xDF; | |
| 1702 static const int WWZX = 0x2F; | |
| 1703 static const int WWZY = 0x6F; | |
| 1704 static const int WWZZ = 0xAF; | |
| 1705 static const int WWZW = 0xEF; | |
| 1706 static const int WWWX = 0x3F; | |
| 1707 static const int WWWY = 0x7F; | |
| 1708 static const int WWWZ = 0xBF; | |
| 1709 static const int WWWW = 0xFF; | |
| 1710 | |
| 1711 /// Shuffle the lane values. [mask] must be one of the 256 shuffle constants. | |
| 1712 Float32x4 shuffle(int m) { | |
| 1713 if ((m < 0) || (m > 255)) { | |
| 1714 throw new RangeError('mask $m must be in the range [0..256)'); | |
| 1715 } | |
| 1716 double _x = _storage[m & 0x3]; | |
| 1717 double _y = _storage[(m >> 2) & 0x3]; | |
| 1718 double _z = _storage[(m >> 4) & 0x3]; | |
| 1719 double _w = _storage[(m >> 6) & 0x3]; | |
| 1720 return new Float32x4(_x, _y, _z, _w); | |
| 1721 } | |
| 1722 | |
| 1723 /// Shuffle the lane values in [this] and [other]. The returned | |
| 1724 /// Float32x4 will have XY lanes from [this] and ZW lanes from [other]. | |
| 1725 /// Uses the same [mask] as [shuffle]. | |
| 1726 Float32x4 shuffleMix(Float32x4 other, int m) { | |
| 1727 if ((m < 0) || (m > 255)) { | |
| 1728 throw new RangeError('mask $m must be in the range [0..256)'); | |
| 1729 } | |
| 1730 double _x = _storage[m & 0x3]; | |
| 1731 double _y = _storage[(m >> 2) & 0x3]; | |
| 1732 double _z = other._storage[(m >> 4) & 0x3]; | |
| 1733 double _w = other._storage[(m >> 6) & 0x3]; | |
| 1734 return new Float32x4(_x, _y, _z, _w); | |
| 1735 } | |
| 1736 | |
| 1737 /// Copy [this] and replace the [x] lane. | |
| 1738 Float32x4 withX(double x) { | |
| 1739 double _x = x; | |
| 1740 double _y = _storage[1]; | |
| 1741 double _z = _storage[2]; | |
| 1742 double _w = _storage[3]; | |
| 1743 return new Float32x4(_x, _y, _z, _w); | |
| 1744 } | |
| 1745 | |
| 1746 /// Copy [this] and replace the [y] lane. | |
| 1747 Float32x4 withY(double y) { | |
| 1748 double _x = _storage[0]; | |
| 1749 double _y = y; | |
| 1750 double _z = _storage[2]; | |
| 1751 double _w = _storage[3]; | |
| 1752 return new Float32x4(_x, _y, _z, _w); | |
| 1753 } | |
| 1754 | |
| 1755 /// Copy [this] and replace the [z] lane. | |
| 1756 Float32x4 withZ(double z) { | |
| 1757 double _x = _storage[0]; | |
| 1758 double _y = _storage[1]; | |
| 1759 double _z = z; | |
| 1760 double _w = _storage[3]; | |
| 1761 return new Float32x4(_x, _y, _z, _w); | |
| 1762 } | |
| 1763 | |
| 1764 /// Copy [this] and replace the [w] lane. | |
| 1765 Float32x4 withW(double w) { | |
| 1766 double _x = _storage[0]; | |
| 1767 double _y = _storage[1]; | |
| 1768 double _z = _storage[2]; | |
| 1769 double _w = w; | |
| 1770 return new Float32x4(_x, _y, _z, _w); | |
| 1771 } | |
| 1772 | |
| 1773 /// Returns the lane-wise minimum value in [this] or [other]. | |
| 1774 Float32x4 min(Float32x4 other) { | |
| 1775 double _x = _storage[0] < other._storage[0] ? | |
| 1776 _storage[0] : other._storage[0]; | |
| 1777 double _y = _storage[1] < other._storage[1] ? | |
| 1778 _storage[1] : other._storage[1]; | |
| 1779 double _z = _storage[2] < other._storage[2] ? | |
| 1780 _storage[2] : other._storage[2]; | |
| 1781 double _w = _storage[3] < other._storage[3] ? | |
| 1782 _storage[3] : other._storage[3]; | |
| 1783 return new Float32x4(_x, _y, _z, _w); | |
| 1784 } | |
| 1785 | |
| 1786 /// Returns the lane-wise maximum value in [this] or [other]. | |
| 1787 Float32x4 max(Float32x4 other) { | |
| 1788 double _x = _storage[0] > other._storage[0] ? | |
| 1789 _storage[0] : other._storage[0]; | |
| 1790 double _y = _storage[1] > other._storage[1] ? | |
| 1791 _storage[1] : other._storage[1]; | |
| 1792 double _z = _storage[2] > other._storage[2] ? | |
| 1793 _storage[2] : other._storage[2]; | |
| 1794 double _w = _storage[3] > other._storage[3] ? | |
| 1795 _storage[3] : other._storage[3]; | |
| 1796 return new Float32x4(_x, _y, _z, _w); | |
| 1797 } | |
| 1798 | |
| 1799 /// Returns the square root of [this]. | |
| 1800 Float32x4 sqrt() { | |
| 1801 double _x = Math.sqrt(_storage[0]); | |
| 1802 double _y = Math.sqrt(_storage[1]); | |
| 1803 double _z = Math.sqrt(_storage[2]); | |
| 1804 double _w = Math.sqrt(_storage[3]); | |
| 1805 return new Float32x4(_x, _y, _z, _w); | |
| 1806 } | |
| 1807 | |
| 1808 /// Returns the reciprocal of [this]. | |
| 1809 Float32x4 reciprocal() { | |
| 1810 double _x = 1.0 / _storage[0]; | |
| 1811 double _y = 1.0 / _storage[1]; | |
| 1812 double _z = 1.0 / _storage[2]; | |
| 1813 double _w = 1.0 / _storage[3]; | |
| 1814 return new Float32x4(_x, _y, _z, _w); | |
| 1815 } | |
| 1816 | |
| 1817 /// Returns the square root of the reciprocal of [this]. | |
| 1818 Float32x4 reciprocalSqrt() { | |
| 1819 double _x = Math.sqrt(1.0 / _storage[0]); | |
| 1820 double _y = Math.sqrt(1.0 / _storage[1]); | |
| 1821 double _z = Math.sqrt(1.0 / _storage[2]); | |
| 1822 double _w = Math.sqrt(1.0 / _storage[3]); | |
| 1823 return new Float32x4(_x, _y, _z, _w); | |
| 1824 } | |
| 1825 } | |
| 1826 | |
| 1827 | |
| 1828 /** | |
| 1829 * Interface of Dart Int32x4 and operations. | |
| 1830 * Int32x4 stores 4 32-bit bit-masks in "lanes". | |
| 1831 * The lanes are "x", "y", "z", and "w" respectively. | |
| 1832 */ | |
| 1833 class Int32x4 { | |
| 1834 final _storage = new Int32List(4); | |
| 1835 | |
| 1836 Int32x4(int x, int y, int z, int w) { | |
| 1837 _storage[0] = x; | |
| 1838 _storage[1] = y; | |
| 1839 _storage[2] = z; | |
| 1840 _storage[3] = w; | |
| 1841 } | |
| 1842 | |
| 1843 Int32x4.bool(bool x, bool y, bool z, bool w) { | |
| 1844 _storage[0] = x == true ? 0xFFFFFFFF : 0x0; | |
| 1845 _storage[1] = y == true ? 0xFFFFFFFF : 0x0; | |
| 1846 _storage[2] = z == true ? 0xFFFFFFFF : 0x0; | |
| 1847 _storage[3] = w == true ? 0xFFFFFFFF : 0x0; | |
| 1848 } | |
| 1849 | |
| 1850 /// Returns a bit-wise copy of [x] as a Int32x4. | |
| 1851 Int32x4.fromFloat32x4Bits(Float32x4 x) { | |
| 1852 var view = new Uint32List.view(x._storage.buffer); | |
| 1853 _storage[0] = view[0]; | |
| 1854 _storage[1] = view[1]; | |
| 1855 _storage[2] = view[2]; | |
| 1856 _storage[3] = view[3]; | |
| 1857 } | |
| 1858 | |
| 1859 String toString() { | |
| 1860 return '[${_storage[0]}, ${_storage[1]}, ${_storage[2]}, ${_storage[3]}]'; | |
| 1861 } | |
| 1862 | |
| 1863 /// The bit-wise or operator. | |
| 1864 Int32x4 operator|(Int32x4 other) { | |
| 1865 int _x = _storage[0] | other._storage[0]; | |
| 1866 int _y = _storage[1] | other._storage[1]; | |
| 1867 int _z = _storage[2] | other._storage[2]; | |
| 1868 int _w = _storage[3] | other._storage[3]; | |
| 1869 return new Int32x4(_x, _y, _z, _w); | |
| 1870 } | |
| 1871 | |
| 1872 /// The bit-wise and operator. | |
| 1873 Int32x4 operator&(Int32x4 other) { | |
| 1874 int _x = _storage[0] & other._storage[0]; | |
| 1875 int _y = _storage[1] & other._storage[1]; | |
| 1876 int _z = _storage[2] & other._storage[2]; | |
| 1877 int _w = _storage[3] & other._storage[3]; | |
| 1878 return new Int32x4(_x, _y, _z, _w); | |
| 1879 } | |
| 1880 | |
| 1881 /// The bit-wise xor operator. | |
| 1882 Int32x4 operator^(Int32x4 other) { | |
| 1883 int _x = _storage[0] ^ other._storage[0]; | |
| 1884 int _y = _storage[1] ^ other._storage[1]; | |
| 1885 int _z = _storage[2] ^ other._storage[2]; | |
| 1886 int _w = _storage[3] ^ other._storage[3]; | |
| 1887 return new Int32x4(_x, _y, _z, _w); | |
| 1888 } | |
| 1889 | |
| 1890 Int32x4 operator+(Int32x4 other) { | |
| 1891 var r = new Int32x4(0, 0, 0, 0); | |
| 1892 r._storage[0] = (_storage[0] + other._storage[0]); | |
| 1893 r._storage[1] = (_storage[1] + other._storage[1]); | |
| 1894 r._storage[2] = (_storage[2] + other._storage[2]); | |
| 1895 r._storage[3] = (_storage[3] + other._storage[3]); | |
| 1896 return r; | |
| 1897 } | |
| 1898 | |
| 1899 Int32x4 operator-(Int32x4 other) { | |
| 1900 var r = new Int32x4(0, 0, 0, 0); | |
| 1901 r._storage[0] = (_storage[0] - other._storage[0]); | |
| 1902 r._storage[1] = (_storage[1] - other._storage[1]); | |
| 1903 r._storage[2] = (_storage[2] - other._storage[2]); | |
| 1904 r._storage[3] = (_storage[3] - other._storage[3]); | |
| 1905 return r; | |
| 1906 } | |
| 1907 | |
| 1908 /// Extract 32-bit mask from x lane. | |
| 1909 int get x => _storage[0]; | |
| 1910 /// Extract 32-bit mask from y lane. | |
| 1911 int get y => _storage[1]; | |
| 1912 /// Extract 32-bit mask from z lane. | |
| 1913 int get z => _storage[2]; | |
| 1914 /// Extract 32-bit mask from w lane. | |
| 1915 int get w => _storage[3]; | |
| 1916 | |
| 1917 /// Extract the top bit from each lane return them in the first 4 bits. | |
| 1918 int get signMask { | |
| 1919 int mx = (_storage[0] & 0x80000000) >> 31; | |
| 1920 int my = (_storage[1] & 0x80000000) >> 31; | |
| 1921 int mz = (_storage[2] & 0x80000000) >> 31; | |
| 1922 int mw = (_storage[3] & 0x80000000) >> 31; | |
| 1923 return mx | my << 1 | mz << 2 | mw << 3; | |
| 1924 } | |
| 1925 | |
| 1926 /// Mask passed to [shuffle] and [shuffleMix]. | |
| 1927 static const int XXXX = 0x0; | |
| 1928 static const int XXXY = 0x40; | |
| 1929 static const int XXXZ = 0x80; | |
| 1930 static const int XXXW = 0xC0; | |
| 1931 static const int XXYX = 0x10; | |
| 1932 static const int XXYY = 0x50; | |
| 1933 static const int XXYZ = 0x90; | |
| 1934 static const int XXYW = 0xD0; | |
| 1935 static const int XXZX = 0x20; | |
| 1936 static const int XXZY = 0x60; | |
| 1937 static const int XXZZ = 0xA0; | |
| 1938 static const int XXZW = 0xE0; | |
| 1939 static const int XXWX = 0x30; | |
| 1940 static const int XXWY = 0x70; | |
| 1941 static const int XXWZ = 0xB0; | |
| 1942 static const int XXWW = 0xF0; | |
| 1943 static const int XYXX = 0x4; | |
| 1944 static const int XYXY = 0x44; | |
| 1945 static const int XYXZ = 0x84; | |
| 1946 static const int XYXW = 0xC4; | |
| 1947 static const int XYYX = 0x14; | |
| 1948 static const int XYYY = 0x54; | |
| 1949 static const int XYYZ = 0x94; | |
| 1950 static const int XYYW = 0xD4; | |
| 1951 static const int XYZX = 0x24; | |
| 1952 static const int XYZY = 0x64; | |
| 1953 static const int XYZZ = 0xA4; | |
| 1954 static const int XYZW = 0xE4; | |
| 1955 static const int XYWX = 0x34; | |
| 1956 static const int XYWY = 0x74; | |
| 1957 static const int XYWZ = 0xB4; | |
| 1958 static const int XYWW = 0xF4; | |
| 1959 static const int XZXX = 0x8; | |
| 1960 static const int XZXY = 0x48; | |
| 1961 static const int XZXZ = 0x88; | |
| 1962 static const int XZXW = 0xC8; | |
| 1963 static const int XZYX = 0x18; | |
| 1964 static const int XZYY = 0x58; | |
| 1965 static const int XZYZ = 0x98; | |
| 1966 static const int XZYW = 0xD8; | |
| 1967 static const int XZZX = 0x28; | |
| 1968 static const int XZZY = 0x68; | |
| 1969 static const int XZZZ = 0xA8; | |
| 1970 static const int XZZW = 0xE8; | |
| 1971 static const int XZWX = 0x38; | |
| 1972 static const int XZWY = 0x78; | |
| 1973 static const int XZWZ = 0xB8; | |
| 1974 static const int XZWW = 0xF8; | |
| 1975 static const int XWXX = 0xC; | |
| 1976 static const int XWXY = 0x4C; | |
| 1977 static const int XWXZ = 0x8C; | |
| 1978 static const int XWXW = 0xCC; | |
| 1979 static const int XWYX = 0x1C; | |
| 1980 static const int XWYY = 0x5C; | |
| 1981 static const int XWYZ = 0x9C; | |
| 1982 static const int XWYW = 0xDC; | |
| 1983 static const int XWZX = 0x2C; | |
| 1984 static const int XWZY = 0x6C; | |
| 1985 static const int XWZZ = 0xAC; | |
| 1986 static const int XWZW = 0xEC; | |
| 1987 static const int XWWX = 0x3C; | |
| 1988 static const int XWWY = 0x7C; | |
| 1989 static const int XWWZ = 0xBC; | |
| 1990 static const int XWWW = 0xFC; | |
| 1991 static const int YXXX = 0x1; | |
| 1992 static const int YXXY = 0x41; | |
| 1993 static const int YXXZ = 0x81; | |
| 1994 static const int YXXW = 0xC1; | |
| 1995 static const int YXYX = 0x11; | |
| 1996 static const int YXYY = 0x51; | |
| 1997 static const int YXYZ = 0x91; | |
| 1998 static const int YXYW = 0xD1; | |
| 1999 static const int YXZX = 0x21; | |
| 2000 static const int YXZY = 0x61; | |
| 2001 static const int YXZZ = 0xA1; | |
| 2002 static const int YXZW = 0xE1; | |
| 2003 static const int YXWX = 0x31; | |
| 2004 static const int YXWY = 0x71; | |
| 2005 static const int YXWZ = 0xB1; | |
| 2006 static const int YXWW = 0xF1; | |
| 2007 static const int YYXX = 0x5; | |
| 2008 static const int YYXY = 0x45; | |
| 2009 static const int YYXZ = 0x85; | |
| 2010 static const int YYXW = 0xC5; | |
| 2011 static const int YYYX = 0x15; | |
| 2012 static const int YYYY = 0x55; | |
| 2013 static const int YYYZ = 0x95; | |
| 2014 static const int YYYW = 0xD5; | |
| 2015 static const int YYZX = 0x25; | |
| 2016 static const int YYZY = 0x65; | |
| 2017 static const int YYZZ = 0xA5; | |
| 2018 static const int YYZW = 0xE5; | |
| 2019 static const int YYWX = 0x35; | |
| 2020 static const int YYWY = 0x75; | |
| 2021 static const int YYWZ = 0xB5; | |
| 2022 static const int YYWW = 0xF5; | |
| 2023 static const int YZXX = 0x9; | |
| 2024 static const int YZXY = 0x49; | |
| 2025 static const int YZXZ = 0x89; | |
| 2026 static const int YZXW = 0xC9; | |
| 2027 static const int YZYX = 0x19; | |
| 2028 static const int YZYY = 0x59; | |
| 2029 static const int YZYZ = 0x99; | |
| 2030 static const int YZYW = 0xD9; | |
| 2031 static const int YZZX = 0x29; | |
| 2032 static const int YZZY = 0x69; | |
| 2033 static const int YZZZ = 0xA9; | |
| 2034 static const int YZZW = 0xE9; | |
| 2035 static const int YZWX = 0x39; | |
| 2036 static const int YZWY = 0x79; | |
| 2037 static const int YZWZ = 0xB9; | |
| 2038 static const int YZWW = 0xF9; | |
| 2039 static const int YWXX = 0xD; | |
| 2040 static const int YWXY = 0x4D; | |
| 2041 static const int YWXZ = 0x8D; | |
| 2042 static const int YWXW = 0xCD; | |
| 2043 static const int YWYX = 0x1D; | |
| 2044 static const int YWYY = 0x5D; | |
| 2045 static const int YWYZ = 0x9D; | |
| 2046 static const int YWYW = 0xDD; | |
| 2047 static const int YWZX = 0x2D; | |
| 2048 static const int YWZY = 0x6D; | |
| 2049 static const int YWZZ = 0xAD; | |
| 2050 static const int YWZW = 0xED; | |
| 2051 static const int YWWX = 0x3D; | |
| 2052 static const int YWWY = 0x7D; | |
| 2053 static const int YWWZ = 0xBD; | |
| 2054 static const int YWWW = 0xFD; | |
| 2055 static const int ZXXX = 0x2; | |
| 2056 static const int ZXXY = 0x42; | |
| 2057 static const int ZXXZ = 0x82; | |
| 2058 static const int ZXXW = 0xC2; | |
| 2059 static const int ZXYX = 0x12; | |
| 2060 static const int ZXYY = 0x52; | |
| 2061 static const int ZXYZ = 0x92; | |
| 2062 static const int ZXYW = 0xD2; | |
| 2063 static const int ZXZX = 0x22; | |
| 2064 static const int ZXZY = 0x62; | |
| 2065 static const int ZXZZ = 0xA2; | |
| 2066 static const int ZXZW = 0xE2; | |
| 2067 static const int ZXWX = 0x32; | |
| 2068 static const int ZXWY = 0x72; | |
| 2069 static const int ZXWZ = 0xB2; | |
| 2070 static const int ZXWW = 0xF2; | |
| 2071 static const int ZYXX = 0x6; | |
| 2072 static const int ZYXY = 0x46; | |
| 2073 static const int ZYXZ = 0x86; | |
| 2074 static const int ZYXW = 0xC6; | |
| 2075 static const int ZYYX = 0x16; | |
| 2076 static const int ZYYY = 0x56; | |
| 2077 static const int ZYYZ = 0x96; | |
| 2078 static const int ZYYW = 0xD6; | |
| 2079 static const int ZYZX = 0x26; | |
| 2080 static const int ZYZY = 0x66; | |
| 2081 static const int ZYZZ = 0xA6; | |
| 2082 static const int ZYZW = 0xE6; | |
| 2083 static const int ZYWX = 0x36; | |
| 2084 static const int ZYWY = 0x76; | |
| 2085 static const int ZYWZ = 0xB6; | |
| 2086 static const int ZYWW = 0xF6; | |
| 2087 static const int ZZXX = 0xA; | |
| 2088 static const int ZZXY = 0x4A; | |
| 2089 static const int ZZXZ = 0x8A; | |
| 2090 static const int ZZXW = 0xCA; | |
| 2091 static const int ZZYX = 0x1A; | |
| 2092 static const int ZZYY = 0x5A; | |
| 2093 static const int ZZYZ = 0x9A; | |
| 2094 static const int ZZYW = 0xDA; | |
| 2095 static const int ZZZX = 0x2A; | |
| 2096 static const int ZZZY = 0x6A; | |
| 2097 static const int ZZZZ = 0xAA; | |
| 2098 static const int ZZZW = 0xEA; | |
| 2099 static const int ZZWX = 0x3A; | |
| 2100 static const int ZZWY = 0x7A; | |
| 2101 static const int ZZWZ = 0xBA; | |
| 2102 static const int ZZWW = 0xFA; | |
| 2103 static const int ZWXX = 0xE; | |
| 2104 static const int ZWXY = 0x4E; | |
| 2105 static const int ZWXZ = 0x8E; | |
| 2106 static const int ZWXW = 0xCE; | |
| 2107 static const int ZWYX = 0x1E; | |
| 2108 static const int ZWYY = 0x5E; | |
| 2109 static const int ZWYZ = 0x9E; | |
| 2110 static const int ZWYW = 0xDE; | |
| 2111 static const int ZWZX = 0x2E; | |
| 2112 static const int ZWZY = 0x6E; | |
| 2113 static const int ZWZZ = 0xAE; | |
| 2114 static const int ZWZW = 0xEE; | |
| 2115 static const int ZWWX = 0x3E; | |
| 2116 static const int ZWWY = 0x7E; | |
| 2117 static const int ZWWZ = 0xBE; | |
| 2118 static const int ZWWW = 0xFE; | |
| 2119 static const int WXXX = 0x3; | |
| 2120 static const int WXXY = 0x43; | |
| 2121 static const int WXXZ = 0x83; | |
| 2122 static const int WXXW = 0xC3; | |
| 2123 static const int WXYX = 0x13; | |
| 2124 static const int WXYY = 0x53; | |
| 2125 static const int WXYZ = 0x93; | |
| 2126 static const int WXYW = 0xD3; | |
| 2127 static const int WXZX = 0x23; | |
| 2128 static const int WXZY = 0x63; | |
| 2129 static const int WXZZ = 0xA3; | |
| 2130 static const int WXZW = 0xE3; | |
| 2131 static const int WXWX = 0x33; | |
| 2132 static const int WXWY = 0x73; | |
| 2133 static const int WXWZ = 0xB3; | |
| 2134 static const int WXWW = 0xF3; | |
| 2135 static const int WYXX = 0x7; | |
| 2136 static const int WYXY = 0x47; | |
| 2137 static const int WYXZ = 0x87; | |
| 2138 static const int WYXW = 0xC7; | |
| 2139 static const int WYYX = 0x17; | |
| 2140 static const int WYYY = 0x57; | |
| 2141 static const int WYYZ = 0x97; | |
| 2142 static const int WYYW = 0xD7; | |
| 2143 static const int WYZX = 0x27; | |
| 2144 static const int WYZY = 0x67; | |
| 2145 static const int WYZZ = 0xA7; | |
| 2146 static const int WYZW = 0xE7; | |
| 2147 static const int WYWX = 0x37; | |
| 2148 static const int WYWY = 0x77; | |
| 2149 static const int WYWZ = 0xB7; | |
| 2150 static const int WYWW = 0xF7; | |
| 2151 static const int WZXX = 0xB; | |
| 2152 static const int WZXY = 0x4B; | |
| 2153 static const int WZXZ = 0x8B; | |
| 2154 static const int WZXW = 0xCB; | |
| 2155 static const int WZYX = 0x1B; | |
| 2156 static const int WZYY = 0x5B; | |
| 2157 static const int WZYZ = 0x9B; | |
| 2158 static const int WZYW = 0xDB; | |
| 2159 static const int WZZX = 0x2B; | |
| 2160 static const int WZZY = 0x6B; | |
| 2161 static const int WZZZ = 0xAB; | |
| 2162 static const int WZZW = 0xEB; | |
| 2163 static const int WZWX = 0x3B; | |
| 2164 static const int WZWY = 0x7B; | |
| 2165 static const int WZWZ = 0xBB; | |
| 2166 static const int WZWW = 0xFB; | |
| 2167 static const int WWXX = 0xF; | |
| 2168 static const int WWXY = 0x4F; | |
| 2169 static const int WWXZ = 0x8F; | |
| 2170 static const int WWXW = 0xCF; | |
| 2171 static const int WWYX = 0x1F; | |
| 2172 static const int WWYY = 0x5F; | |
| 2173 static const int WWYZ = 0x9F; | |
| 2174 static const int WWYW = 0xDF; | |
| 2175 static const int WWZX = 0x2F; | |
| 2176 static const int WWZY = 0x6F; | |
| 2177 static const int WWZZ = 0xAF; | |
| 2178 static const int WWZW = 0xEF; | |
| 2179 static const int WWWX = 0x3F; | |
| 2180 static const int WWWY = 0x7F; | |
| 2181 static const int WWWZ = 0xBF; | |
| 2182 static const int WWWW = 0xFF; | |
| 2183 | |
| 2184 /// Shuffle the lane values. [mask] must be one of the 256 shuffle constants. | |
| 2185 Int32x4 shuffle(int mask) { | |
| 2186 if ((mask < 0) || (mask > 255)) { | |
| 2187 throw new RangeError('mask $mask must be in the range [0..256)'); | |
| 2188 } | |
| 2189 int _x = _storage[mask & 0x3]; | |
| 2190 int _y = _storage[(mask >> 2) & 0x3]; | |
| 2191 int _z = _storage[(mask >> 4) & 0x3]; | |
| 2192 int _w = _storage[(mask >> 6) & 0x3]; | |
| 2193 return new Int32x4(_x, _y, _z, _w); | |
| 2194 } | |
| 2195 | |
| 2196 /// Shuffle the lane values in [this] and [other]. The returned | |
| 2197 /// Int32x4 will have XY lanes from [this] and ZW lanes from [other]. | |
| 2198 /// Uses the same [mask] as [shuffle]. | |
| 2199 Int32x4 shuffleMix(Int32x4 other, int mask) { | |
| 2200 if ((mask < 0) || (mask > 255)) { | |
| 2201 throw new RangeError('mask $mask must be in the range [0..256)'); | |
| 2202 } | |
| 2203 int _x = _storage[mask & 0x3]; | |
| 2204 int _y = _storage[(mask >> 2) & 0x3]; | |
| 2205 int _z = other._storage[(mask >> 4) & 0x3]; | |
| 2206 int _w = other._storage[(mask >> 6) & 0x3]; | |
| 2207 return new Int32x4(_x, _y, _z, _w); | |
| 2208 } | |
| 2209 | |
| 2210 /// Returns a new [Int32x4] copied from [this] with a new x value. | |
| 2211 Int32x4 withX(int x) { | |
| 2212 int _x = x; | |
| 2213 int _y = _storage[1]; | |
| 2214 int _z = _storage[2]; | |
| 2215 int _w = _storage[3]; | |
| 2216 return new Int32x4(_x, _y, _z, _w); | |
| 2217 } | |
| 2218 | |
| 2219 /// Returns a new [Int32x4] copied from [this] with a new y value. | |
| 2220 Int32x4 withY(int y) { | |
| 2221 int _x = _storage[0]; | |
| 2222 int _y = y; | |
| 2223 int _z = _storage[2]; | |
| 2224 int _w = _storage[3]; | |
| 2225 return new Int32x4(_x, _y, _z, _w); | |
| 2226 } | |
| 2227 | |
| 2228 /// Returns a new [Int32x4] copied from [this] with a new z value. | |
| 2229 Int32x4 withZ(int z) { | |
| 2230 int _x = _storage[0]; | |
| 2231 int _y = _storage[1]; | |
| 2232 int _z = z; | |
| 2233 int _w = _storage[3]; | |
| 2234 return new Int32x4(_x, _y, _z, _w); | |
| 2235 } | |
| 2236 | |
| 2237 /// Returns a new [Int32x4] copied from [this] with a new w value. | |
| 2238 Int32x4 withW(int w) { | |
| 2239 int _x = _storage[0]; | |
| 2240 int _y = _storage[1]; | |
| 2241 int _z = _storage[2]; | |
| 2242 int _w = w; | |
| 2243 return new Int32x4(_x, _y, _z, _w); | |
| 2244 } | |
| 2245 | |
| 2246 /// Extracted x value. Returns false for 0, true for any other value. | |
| 2247 bool get flagX => _storage[0] != 0x0; | |
| 2248 /// Extracted y value. Returns false for 0, true for any other value. | |
| 2249 bool get flagY => _storage[1] != 0x0; | |
| 2250 /// Extracted z value. Returns false for 0, true for any other value. | |
| 2251 bool get flagZ => _storage[2] != 0x0; | |
| 2252 /// Extracted w value. Returns false for 0, true for any other value. | |
| 2253 bool get flagW => _storage[3] != 0x0; | |
| 2254 | |
| 2255 /// Returns a new [Int32x4] copied from [this] with a new x value. | |
| 2256 Int32x4 withFlagX(bool x) { | |
| 2257 int _x = x == true ? 0xFFFFFFFF : 0x0; | |
| 2258 int _y = _storage[1]; | |
| 2259 int _z = _storage[2]; | |
| 2260 int _w = _storage[3]; | |
| 2261 return new Int32x4(_x, _y, _z, _w); | |
| 2262 } | |
| 2263 | |
| 2264 /// Returns a new [Int32x4] copied from [this] with a new y value. | |
| 2265 Int32x4 withFlagY(bool y) { | |
| 2266 int _x = _storage[0]; | |
| 2267 int _y = y == true ? 0xFFFFFFFF : 0x0; | |
| 2268 int _z = _storage[2]; | |
| 2269 int _w = _storage[3]; | |
| 2270 return new Int32x4(_x, _y, _z, _w); | |
| 2271 } | |
| 2272 | |
| 2273 /// Returns a new [Int32x4] copied from [this] with a new z value. | |
| 2274 Int32x4 withFlagZ(bool z) { | |
| 2275 int _x = _storage[0]; | |
| 2276 int _y = _storage[1]; | |
| 2277 int _z = z == true ? 0xFFFFFFFF : 0x0; | |
| 2278 int _w = _storage[3]; | |
| 2279 return new Int32x4(_x, _y, _z, _w); | |
| 2280 } | |
| 2281 | |
| 2282 /// Returns a new [Int32x4] copied from [this] with a new w value. | |
| 2283 Int32x4 withFlagW(bool w) { | |
| 2284 int _x = _storage[0]; | |
| 2285 int _y = _storage[1]; | |
| 2286 int _z = _storage[2]; | |
| 2287 int _w = w == true ? 0xFFFFFFFF : 0x0; | |
| 2288 return new Int32x4(_x, _y, _z, _w); | |
| 2289 } | |
| 2290 | |
| 2291 /// Merge [trueValue] and [falseValue] based on [this]' bit mask: | |
| 2292 /// Select bit from [trueValue] when bit in [this] is on. | |
| 2293 /// Select bit from [falseValue] when bit in [this] is off. | |
| 2294 Float32x4 select(Float32x4 trueValue, Float32x4 falseValue) { | |
| 2295 var trueView = new Int32List.view(trueValue._storage.buffer); | |
| 2296 var falseView = new Int32List.view(falseValue._storage.buffer); | |
| 2297 int cmx = _storage[0]; | |
| 2298 int cmy = _storage[1]; | |
| 2299 int cmz = _storage[2]; | |
| 2300 int cmw = _storage[3]; | |
| 2301 int stx = trueView[0]; | |
| 2302 int sty = trueView[1]; | |
| 2303 int stz = trueView[2]; | |
| 2304 int stw = trueView[3]; | |
| 2305 int sfx = falseView[0]; | |
| 2306 int sfy = falseView[1]; | |
| 2307 int sfz = falseView[2]; | |
| 2308 int sfw = falseView[3]; | |
| 2309 int _x = (cmx & stx) | (~cmx & sfx); | |
| 2310 int _y = (cmy & sty) | (~cmy & sfy); | |
| 2311 int _z = (cmz & stz) | (~cmz & sfz); | |
| 2312 int _w = (cmw & stw) | (~cmw & sfw); | |
| 2313 var r = new Float32x4(0.0, 0.0, 0.0, 0.0); | |
| 2314 var rView = new Int32List.view(r._storage.buffer); | |
| 2315 rView[0] = _x; | |
| 2316 rView[1] = _y; | |
| 2317 rView[2] = _z; | |
| 2318 rView[3] = _w; | |
| 2319 return r; | |
| 2320 } | |
| 2321 } | |
| 2322 | |
| 2323 class Float64x2 { | |
| 2324 final _storage = new Float64List(2); | |
| 2325 | |
| 2326 Float64x2(double x, double y) { | |
| 2327 _storage[0] = x; | |
| 2328 _storage[1] = y; | |
| 2329 } | |
| 2330 | |
| 2331 Float64x2.splat(double v) { | |
| 2332 _storage[0] = v; | |
| 2333 _storage[1] = v; | |
| 2334 } | |
| 2335 | |
| 2336 Float64x2.zero(); | |
| 2337 | |
| 2338 Float64x2.fromFloat32x4(Float32x4 v) { | |
| 2339 _storage[0] = v._storage[0]; | |
| 2340 _storage[1] = v._storage[1]; | |
| 2341 } | |
| 2342 | |
| 2343 String toString() { | |
| 2344 return '[${_storage[0]}, ${_storage[1]}]'; | |
| 2345 } | |
| 2346 | |
| 2347 /// Addition operator. | |
| 2348 Float64x2 operator+(Float64x2 other) { | |
| 2349 return new Float64x2(_storage[0] + other._storage[0], | |
| 2350 _storage[1] + other._storage[1]); | |
| 2351 } | |
| 2352 | |
| 2353 /// Negate operator. | |
| 2354 Float64x2 operator-() { | |
| 2355 return new Float64x2(-_storage[0], -_storage[1]); | |
| 2356 } | |
| 2357 | |
| 2358 /// Subtraction operator. | |
| 2359 Float64x2 operator-(Float64x2 other) { | |
| 2360 return new Float64x2(_storage[0] - other._storage[0], | |
| 2361 _storage[1] - other._storage[1]); | |
| 2362 } | |
| 2363 /// Multiplication operator. | |
| 2364 Float64x2 operator*(Float64x2 other) { | |
| 2365 return new Float64x2(_storage[0] * other._storage[0], | |
| 2366 _storage[1] * other._storage[1]); | |
| 2367 } | |
| 2368 /// Division operator. | |
| 2369 Float64x2 operator/(Float64x2 other) { | |
| 2370 return new Float64x2(_storage[0] / other._storage[0], | |
| 2371 _storage[1] / other._storage[1]); | |
| 2372 } | |
| 2373 | |
| 2374 /// Returns a copy of [this] each lane being scaled by [s]. | |
| 2375 Float64x2 scale(double s) { | |
| 2376 return new Float64x2(_storage[0] * s, _storage[1] * s); | |
| 2377 } | |
| 2378 | |
| 2379 /// Returns the absolute value of this [Float64x2]. | |
| 2380 Float64x2 abs() { | |
| 2381 return new Float64x2(_storage[0].abs(), _storage[1].abs()); | |
| 2382 } | |
| 2383 | |
| 2384 /// Clamps [this] to be in the range [lowerLimit]-[upperLimit]. | |
| 2385 Float64x2 clamp(Float64x2 lowerLimit, | |
| 2386 Float64x2 upperLimit) { | |
| 2387 double _lx = lowerLimit._storage[0]; | |
| 2388 double _ly = lowerLimit._storage[1]; | |
| 2389 double _ux = upperLimit._storage[0]; | |
| 2390 double _uy = upperLimit._storage[1]; | |
| 2391 double _x = _storage[0]; | |
| 2392 double _y = _storage[1]; | |
| 2393 // MAX(MIN(self, upper), lower). | |
| 2394 _x = _x > _ux ? _ux : _x; | |
| 2395 _y = _y > _uy ? _uy : _y; | |
| 2396 _x = _x < _lx ? _lx : _x; | |
| 2397 _y = _y < _ly ? _ly : _y; | |
| 2398 return new Float64x2(_x, _y); | |
| 2399 } | |
| 2400 | |
| 2401 /// Extracted x value. | |
| 2402 double get x => _storage[0]; | |
| 2403 /// Extracted y value. | |
| 2404 double get y => _storage[1]; | |
| 2405 | |
| 2406 /// Extract the sign bits from each lane return them in the first 2 bits. | |
| 2407 int get signMask { | |
| 2408 var view = new Uint32List.view(_storage.buffer); | |
| 2409 var mx = (view[1] & 0x80000000) >> 31; | |
| 2410 var my = (view[3] & 0x80000000) >> 31; | |
| 2411 return mx | my << 1; | |
| 2412 } | |
| 2413 | |
| 2414 /// Returns a new [Float64x2] copied from [this] with a new x value. | |
| 2415 Float64x2 withX(double x) { | |
| 2416 return new Float64x2(x, _storage[1]); | |
| 2417 } | |
| 2418 | |
| 2419 /// Returns a new [Float64x2] copied from [this] with a new y value. | |
| 2420 Float64x2 withY(double y) { | |
| 2421 return new Float64x2(_storage[0], y); | |
| 2422 } | |
| 2423 | |
| 2424 /// Returns the lane-wise minimum value in [this] or [other]. | |
| 2425 Float64x2 min(Float64x2 other) { | |
| 2426 return new Float64x2( | |
| 2427 _storage[0] < other._storage[0] ? _storage[0] : other._storage[0], | |
| 2428 _storage[1] < other._storage[1] ? _storage[1] : other._storage[1]); | |
| 2429 | |
| 2430 } | |
| 2431 | |
| 2432 /// Returns the lane-wise maximum value in [this] or [other]. | |
| 2433 Float64x2 max(Float64x2 other) { | |
| 2434 return new Float64x2( | |
| 2435 _storage[0] > other._storage[0] ? _storage[0] : other._storage[0], | |
| 2436 _storage[1] > other._storage[1] ? _storage[1] : other._storage[1]); | |
| 2437 } | |
| 2438 | |
| 2439 /// Returns the lane-wise square root of [this]. | |
| 2440 Float64x2 sqrt() { | |
| 2441 return new Float64x2(Math.sqrt(_storage[0]), Math.sqrt(_storage[1])); | |
| 2442 } | |
| 2443 } | |
| 2444 | |
| OLD | NEW |