Commit 83638257 authored by Yoann Pigné's avatar Yoann Pigné

dataview implementation for firefox

parent be213c43
/*
* DataView.js:
* An implementation of the DataView class on top of typed arrays.
* Useful for Firefox 4 which implements TypedArrays but not DataView.
*
* Copyright 2011 by David Flanagan
* http://creativecommons.org/licenses/by-nc-sa/3.0/
*/
(function(global) {
"use strict";
// If DataView already exists, do nothing
if (global.DataView) {
return;
}
var fail = function(msg) {
throw new Error(msg);
};
// If ArrayBuffer is not supported, fail with an error
if (!global.ArrayBuffer) {
fail("ArrayBuffer not supported");
}
// If ES5 is not supported, fail
if (!Object.defineProperties) {
fail("This module requires ECMAScript 5");
}
// Figure if the platform is natively little-endian.
// If the integer 0x00000001 is arranged in memory as 01 00 00 00 then
// we're on a little endian platform. On a big-endian platform we'd get
// get bytes 00 00 00 01 instead.
var nativele = new Int8Array(new Int32Array([1]).buffer)[0] === 1;
// A temporary array for copying or reversing bytes into.
// Since js is single-threaded, we only need this one static copy
var temp = new Uint8Array(8);
// The get() utility function used by the get methods
var get = function (view, type, size, offset, le) {
var i = 0;
if (offset === undefined) {
fail("Missing required offset argument");
}
if (offset < 0 || offset + size > view.byteLength) {
fail("Invalid index: " + offset);
}
if (size === 1 || le === nativele) {
// This is the easy case: the desired endianness
// matches the native endianness.
// Typed arrays require proper alignment. DataView does not.
if ((view.byteOffset + offset) % size === 0) {
return (new type(view.buffer, view.byteOffset + offset, 1))[0];
}
// Copy bytes into the temp array, to fix alignment
for (i=0; i < size; i++)
temp[i] = view._bytes[offset + i];
// Now wrap that buffer with an array of the desired type
return (new type(temp.buffer))[0];
} else {
// If the native endianness doesn't match the desired, then
// we have to reverse the bytes
for (i = 0; i < size; i++) {
temp[size - i - 1] = view._bytes[offset + i];
}
return (new type(temp.buffer))[0];
}
};
// The set() utility function used by the set methods
var set = function(view, type, size, offset, value, le) {
var i = 0;
if (offset === undefined) {
fail("Missing required offset argument");
}
if (value === undefined) {
fail("Missing required value argument");
}
if (offset < 0 || offset + size > view.byteLength) {
fail("Invalid index: " + offset);
}
if (size === 1 || le === nativele) {
// This is the easy case: the desired endianness
// matches the native endianness.
if ((view.byteOffset + offset) % size === 0) {
(new type(view.buffer, view.byteOffset + offset, 1))[0] = value;
}
else {
(new type(temp.buffer))[0] = value;
// Now copy the bytes into the view's buffer
for (i = 0; i < size; i++)
view._bytes[i + offset] = temp[i];
}
} else {
// If the native endianness doesn't match the desired, then
// we have to reverse the bytes
// Store the value into our temporary buffer
(new type(temp.buffer))[0] = value;
// Now copy the bytes, in reverse order, into the view's buffer
for (i = 0; i < size; i++)
view._bytes[offset + i] = temp[size - 1 - i];
}
};
// The DataView() constructor
global.DataView = function DataView(buffer, offset, length) {
if (! (buffer instanceof ArrayBuffer)) {
fail("Bad ArrayBuffer");
}
// Default values for omitted arguments
offset = offset || 0;
length = length || (buffer.byteLength - offset);
if (offset < 0 || length < 0 || offset + length > buffer.byteLength) {
fail("Illegal offset and/or length");
}
// Define the 3 read-only, non-enumerable ArrayBufferView properties
Object.defineProperties(this, {
buffer: {
value: buffer,
enumerable: false,
writable: false,
configurable: false
},
byteOffset: {
value: offset,
enumerable: false,
writable: false,
configurable: false
},
byteLength: {
value: length,
enumerable: false,
writable: false,
configurable: false
},
_bytes: {
value: new Uint8Array(buffer, offset, length),
enumerable: false,
writable: false,
configurable: false
}
});
};
// The DataView prototype object
global.DataView.prototype = {
constructor: DataView,
getInt8: function getInt8(offset) {
return get(this, Int8Array, 1, offset);
},
getUint8: function getUint8(offset) {
return get(this, Uint8Array, 1, offset);
},
getInt16: function getInt16(offset, le) {
return get(this, Int16Array, 2, offset, le);
},
getUint16: function getUint16(offset, le) {
return get(this, Uint16Array, 2, offset, le);
},
getInt32: function getInt32(offset, le) {
return get(this, Int32Array, 4, offset, le);
},
getUint32: function getUint32(offset, le) {
return get(this, Uint32Array, 4, offset, le);
},
getFloat32: function getFloat32(offset, le) {
return get(this, Float32Array, 4, offset, le);
},
getFloat64: function getFloat32(offset, le) {
return get(this, Float64Array, 8, offset, le);
},
setInt8: function setInt8(offset, value) {
set(this, Int8Array, 1, offset, value);
},
setUint8: function setUint8(offset, value) {
set(this, Uint8Array, 1, offset, value);
},
setInt16: function setInt16(offset, value, le) {
set(this, Int16Array, 2, offset, value, le);
},
setUint16: function setUint16(offset, value, le) {
set(this, Uint16Array, 2, offset, value, le);
},
setInt32: function setInt32(offset, value, le) {
set(this, Int32Array, 4, offset, value, le);
},
setUint32: function setUint32(offset, value, le) {
set(this, Uint32Array, 4, offset, value, le);
},
setFloat32: function setFloat32(offset, value, le) {
set(this, Float32Array, 4, offset, value, le);
},
setFloat64: function setFloat64(offset, value, le) {
set(this, Float64Array, 8, offset, value, le);
}
};
} (this));
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment