add IE support (tested in 8 and 9), updated doc and demo, and made getSt... #7

Merged
merged 1 commit into from Dec 21, 2011
View
@@ -115,12 +115,11 @@ You can use a <a href="http://blog.vjeux.com/2011/javascript/jquery-binary-ajax.
```javascript
$.get(
'data.bin',
- function (data) {
- var view = new jDataView(data);
+ function (view) {
var tag = view.getString(4); // 'MD20'
var version = view.getUint32(); // 732
},
- 'binary'
+ 'dataview'
);
```
@@ -1,4 +1,4 @@
-<script src="../../src/jquery-1.4.4-binary-ajax.js"></script>
+<script src="../../jquery/jquery-1.4.4-binary-ajax.js"></script>
<script src="../../src/jdataview.js"></script>
<style>
@@ -15,7 +15,7 @@
// console.log(view.getUint32(0, false));
// view.seek(0);
- while (view.tell() < view.length) {
+ while (view.tell() < view.byteLength) {
// Parse the file meta data
var metadata = {
name: view.getString(100).replace(/\0+$/, ''),
@@ -62,4 +62,4 @@
// Download the file
$.get('jquery.tar', tar, 'binary');
-</script>
+</script>
@@ -0,0 +1,62 @@
+<script src="../../jquery/jquery-1.7.1-binary-ajax.js"></script>
+<script src="../../src/jdataview.js"></script>
+
+<style>
+textarea { width: 80%; height: 300px; }
+</style>
+<p>Content of the file <a href="jquery.tar">jquery.tar</a></p>
+
+<script>
+function tar(view) {
+// console.log(view.getUint32(0, true));
+// console.log(view.getUint32(0, false));
+// view.seek(0);
+
+ while (view.tell() < view.byteLength) {
+ // Parse the file meta data
+ var metadata = {
+ name: view.getString(100).replace(/\0+$/, ''),
+ mode: parseInt(view.getString(8), 8),
+ owner: parseInt(view.getString(8), 8),
+ group: parseInt(view.getString(8), 8),
+ size: parseInt(view.getString(12), 8),
+ modtime: parseInt(view.getString(12), 8),
+ checksum: parseInt(view.getString(8), 8),
+ link: view.getChar(),
+ name_linked: view.getString(100).replace(/\0+$/, ''),
+ ustar: view.getString(6),
+ ustar_version: parseInt(view.getString(2), 8),
+ owner_name: view.getString(32).replace(/\0+$/, ''),
+ group_name: view.getString(32).replace(/\0+$/, ''),
+ device: [parseInt(view.getString(8), 8), parseInt(view.getString(8), 8)],
+ name_prefix: view.getString(155).replace(/\0+$/, '')
+ };
+
+ // Padding
+ if (view.tell() % 512 !== 0) {
+ view.seek(view.tell() + 512 - (view.tell() % 512));
+ }
+
+ // Get the file
+ if (isNaN(metadata.size)) {
+ break;
+ }
+ var content = view.getString(metadata.size);
+
+ // Padding
+ if (view.tell() % 512 != 0) {
+ view.seek(view.tell() + 512 - (view.tell() % 512));
+ }
+
+ // Print the file
+ $('body').append($('<pre></pre>').html(JSON.stringify(metadata, null, ' ')));
+ if (metadata.size) {
+ $('body').append($('<textarea></textarea>').val(content));
+ }
+ }
+}
+
+// Download the file
+$.get('jquery.tar', tar, 'dataview');
+
+</script>
View
@@ -132,14 +132,12 @@ jDataView.prototype = {
if (this._isNodeBuffer) {
value = this.buffer.toString('ascii', this._start + byteOffset, this._start + byteOffset + length);
}
- else if (this._isArrayBuffer) {
+ else {
value = '';
for (var i = 0; i < length; ++i) {
var char = this.getUint8(byteOffset + i);
value += String.fromCharCode(char > 127 ? 65533 : char);
}
- } else {
- value = this.buffer.substr(this._start + byteOffset, length);
}
this._offset = byteOffset + length;
@@ -365,6 +363,62 @@ if (typeof module !== 'undefined') {
}
if (typeof jQuery !== 'undefined' && jQuery.fn.jquery >= "1.6.2") {
+ var convertResponseBodyToText = function (byteArray) {
+ // http://jsperf.com/vbscript-binary-download/6
+ var scrambledStr;
+ try {
+ scrambledStr = IEBinaryToArray_ByteStr(byteArray);
+ } catch (e) {
+ // http://stackoverflow.com/questions/1919972/how-do-i-access-xhr-responsebody-for-binary-data-from-javascript-in-ie
+ // http://miskun.com/javascript/internet-explorer-and-binary-files-data-access/
+ var IEBinaryToArray_ByteStr_Script =
+ "Function IEBinaryToArray_ByteStr(Binary)\r\n"+
+ " IEBinaryToArray_ByteStr = CStr(Binary)\r\n"+
+ "End Function\r\n"+
+ "Function IEBinaryToArray_ByteStr_Last(Binary)\r\n"+
+ " Dim lastIndex\r\n"+
+ " lastIndex = LenB(Binary)\r\n"+
+ " if lastIndex mod 2 Then\r\n"+
+ " IEBinaryToArray_ByteStr_Last = AscB( MidB( Binary, lastIndex, 1 ) )\r\n"+
+ " Else\r\n"+
+ " IEBinaryToArray_ByteStr_Last = -1\r\n"+
+ " End If\r\n"+
+ "End Function\r\n";
+
+ // http://msdn.microsoft.com/en-us/library/ms536420(v=vs.85).aspx
+ // proprietary IE function
+ window.execScript(IEBinaryToArray_ByteStr_Script, 'vbscript');
+
+ scrambledStr = IEBinaryToArray_ByteStr(byteArray);
+ }
+
+ var lastChr = IEBinaryToArray_ByteStr_Last(byteArray),
+ result = "",
+ i = 0,
+ l = scrambledStr.length % 8,
+ thischar;
+ while (i < l) {
+ thischar = scrambledStr.charCodeAt(i++);
+ result += String.fromCharCode(thischar & 0xff, thischar >> 8);
+ }
+ l = scrambledStr.length
+ while (i < l) {
+ result += String.fromCharCode(
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8,
+ (thischar = scrambledStr.charCodeAt(i++), thischar & 0xff), thischar >> 8);
+ }
+ if (lastChr > -1) {
+ result += String.fromCharCode(lastChr);
+ }
+ return result;
+ };
+
jQuery.ajaxSetup({
converters: {
'* dataview': function(data) {
@@ -384,6 +438,10 @@ if (typeof jQuery !== 'undefined' && jQuery.fn.jquery >= "1.6.2") {
else if ('responseType' in xhr && xhr.responseType === 'arraybuffer' && xhr.response) {
responses.text = xhr.response;
}
+ // Internet Explorer (Byte array accessible through VBScript -- convert to text)
+ else if ('responseBody' in xhr) {
+ responses.text = convertResponseBodyToText(xhr.responseBody);
+ }
// Older Browsers
else {
responses.text = xhr.responseText;