读取“二进制” JS 中文件中的字符?

发布于 2024-12-15 23:40:33 字数 269 浏览 0 评论 0原文

现在,当我说二进制时,我的意思是 ghjkl54╞←‼╝454┴ 而不是 10101110

我想用 JavaScript 加载瓦片地图,但我不想重写用 Java 编写的地图编辑器,它将地图导出为二进制文件。所以我想知道,如果可能的话,我该怎么做?

另外,如果不可能,我是否应该读取只有 [width][height][tilenum],[[tilenum2],tilenum3],...] 的tilemap结构?

Now when I say binary, I mean ghjkl54╞←‼╝454┴ and not 10101110.

I wanna load a tilemap in JavaScript, but I don't want to rewrite my map editor, written in Java, which exports maps as binary files. So I was wondering, if it's possible, how would I do this?

Also, if it isn't possible, should I read a tilemap structure where I only have [width][height][tilenum],[[tilenum2], tilenum3],...]?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

遥远的绿洲 2024-12-22 23:40:33

是的,使用 HTML5 文件 API,您可以读取文件的内容。请注意,并非所有浏览器都支持此功能。

通过使用 FileReader 并使用 readAsBinaryString,您可以获得这些字符: http://jsfiddle.net/S4mEv/3/

// bind a <input type="file">'s onchange event to a function
// (does not require jQuery, just for convenience here)
$('#file').change(function() {
    var fr = new FileReader; // create a file reader

    fr.onloadend = function() { // when reading has finished
        alert(fr.result); // alert the contents
    };

    fr.readAsBinaryString(this.files[0]); // start reading
});

Yes, using the HTML5 File API you can read a file's contents. Note that this is not yet supported in all browsers.

By using a FileReader and using readAsBinaryString, you can get those characters: http://jsfiddle.net/S4mEv/3/.

// bind a <input type="file">'s onchange event to a function
// (does not require jQuery, just for convenience here)
$('#file').change(function() {
    var fr = new FileReader; // create a file reader

    fr.onloadend = function() { // when reading has finished
        alert(fr.result); // alert the contents
    };

    fr.readAsBinaryString(this.files[0]); // start reading
});
小耗子 2024-12-22 23:40:33

这个问题对我来说不是很清楚,您是否需要帮助来实际将文件转换为 javascript 二进制字符串或读取已经采用 javascript 二进制字符串格式的文件?如果是后者,也许我的回答会有所帮助。

我在 javascript 中创建并使用了一个类来执行这些操作,其工作原理如下:

//binaryString = result from readAsBinaryString
    var tileReader = new ByteReader( binaryString ), doubles = [];

        while( !tileReader.EOF() ) {
        doubles.push( tileReader.readDouble() );
        } //Read the whole file as big endian doubles

该类:

    function ByteReader( bytedata ) {
    this._data = bytedata || "";
    this._offset = 0;
    }

    ByteReader.prototype = {

        constructor: ByteReader,

        EOF: function(){
        return this._offset >= this._data.length;
        },

        tellSize: function(){
        return this._data.length;
        },

        seekTo: function( offset ){
        this._offset = offset;
        return this;
        },

        rewind: function() {
        this._offset = 0;
        return this;
        },

        readBytes: function( bytes ) {
        var s = this._data.substr( this._offset, bytes );
        this._offset += bytes;
        return s;
        },

        setByteStream: function( data ) {

            if( typeof data != "string" )
            throw new TypeError( typeof data + " must be string" );

        this._data = data;
        this._offset = 0;
        return this;
        },

        readDouble: function( littleEndian ) {
        var s = this.readBytes( 8 );
        var pow = Math.pow, sign, exponent, fraction;

            if( littleEndian )
            s = s.split("").reverse().join("");

        sign =  ( s.charCodeAt(0) & 0x80 ) >> 7;
        exponent =  ( ( s.charCodeAt(0) & 0x7F ) << 4 ) | ( ( s.charCodeAt(1) & 0xF0 ) >> 4 );
        fraction =  ( ( s.charCodeAt(1) & 0x0F ) * pow(2, 48) ) +
                s.charCodeAt(2) * pow( 2, 40 ) +
                s.charCodeAt(3) * pow( 2, 32 ) +
                ( ( s.charCodeAt(4) & 0xFF ) << 24 ) +
                ( ( s.charCodeAt(5) & 0xFF ) << 16 ) +
                ( ( s.charCodeAt(6) & 0xFF ) << 8  ) +
                s.charCodeAt(7);

        sign = pow( -1, sign );

            if( exponent === 2047 ) {
                if( f !== 0)
                return Number.NaN;

                else if( sign < 0 )
                return -Infinity;

                else
                return Infinity;
            }
            else if( exponent > 0 )
            return sign * Math.pow( 2, exponent - 1023 ) * ( fraction / 0x10000000000000 + 1 );


            else if ( fraction !== 0 )
            return sign * Math.pow( 2, -1022 ) * ( fraction / 0x10000000000000 );


            else 
            return 0;

        },

        readSingle: function( littleEndian ) {
        var s = this.readBytes( 4 )
        var sign, exponent, fraction;

            if( littleEndian )
            s = s.split("").reverse().join("");

        sign =  ( s.charCodeAt(0) & 0x80 ) >> 7;
        exponent =  ( ( s.charCodeAt(0) & 0x7F ) << 1 )  | ( ( s.charCodeAt(1) & 0x80 ) >> 7 );
        fraction =  ( ( s.charCodeAt(1) & 0x7F ) << 16 ) |
                ( ( s.charCodeAt(2) & 0xFF ) << 8 )  |
                ( s.charCodeAt(3) & 0xFF );

        sign = Math.pow( -1, sign );

            if( exponent === 255 ) {

                if( fraction !== 0 )
                return Number.Nan;

                else if( sign < 0 )
                return -Infinity;

                else
                return Infinity;
            }
            else if( exponent > 0 )
            return sign * Math.pow(2, exponent - 127) * ( fraction / 0x800000 + 1 );

            else if ( fraction !== 0 )
            return sign *  Math.pow(2, -126) * ( fraction / 0x800000 );

            else
            return 0;

        },

        readSByte: function() {
        var s = this.readBytes( 1 ).charCodeAt( 0 ) & 0xFF;
        return ( s ^ 0x80 ) - 0x80;
        },

        readUByte: function() {
        return this.readBytes( 1 ).charCodeAt( 0 ) & 0xFF;
        },

        readUShort: function( littleEndian ) {
        var s = this.readBytes( 2 );

            if( littleEndian )
            return ( s.charCodeAt( 0 ) & 0xFF ) |
            ( ( s.charCodeAt( 1 ) & 0xFF) << 8 );

            else
            return ( s.charCodeAt( 1 ) & 0xFF ) |
            ( ( s.charCodeAt( 0 ) & 0xFF) << 8 );
        },

        readULong: function( littleEndian ) {
        var s = this.readBytes( 4 ), r;

            if( littleEndian ) 
            r = ( s.charCodeAt( 0 ) & 0xFF )        |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 3 ) & 0xFF ) << 24 );

            else
            r = ( s.charCodeAt( 3 ) & 0xFF )        |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 0 ) & 0xFF ) << 24 );

            if ( r & 0x80000000 )
            r = ( r & 0x7FFFFFFF ) + 0x80000000;

        return r;
        },

        readSShort: function( littleEndian ){
        var s = this.readBytes( 2 ), r;

            if( littleEndian )
            r = ( s.charCodeAt( 0 ) & 0xFF ) |
            ( ( s.charCodeAt( 1 ) & 0xFF) << 8 );

            else
            r = ( s.charCodeAt( 1 ) & 0xFF ) |
            ( ( s.charCodeAt( 0 ) & 0xFF) << 8 );

        return ( r ^ 0x8000 ) - 0x8000;
        },

        readSLong: function( littleEndian ){
        var s = this.readBytes( 4 ), r;

            if( littleEndian ) 
            return ( s.charCodeAt( 0 ) & 0xFF ) |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 3 ) & 0xFF ) << 24 );

            else
            return ( s.charCodeAt( 3 ) & 0xFF ) |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 0 ) & 0xFF ) << 24 );

        }


    };

已使用 .wav 文件进行了大量测试。

The problem is not very clear to me, do you need help with actually getting a file into javascript binary string or reading a file that is already in javascript binary string format? If latter, maybe my answer could help.

I have made and used a class in javascript for these operations that works like this:

//binaryString = result from readAsBinaryString
    var tileReader = new ByteReader( binaryString ), doubles = [];

        while( !tileReader.EOF() ) {
        doubles.push( tileReader.readDouble() );
        } //Read the whole file as big endian doubles

The class:

    function ByteReader( bytedata ) {
    this._data = bytedata || "";
    this._offset = 0;
    }

    ByteReader.prototype = {

        constructor: ByteReader,

        EOF: function(){
        return this._offset >= this._data.length;
        },

        tellSize: function(){
        return this._data.length;
        },

        seekTo: function( offset ){
        this._offset = offset;
        return this;
        },

        rewind: function() {
        this._offset = 0;
        return this;
        },

        readBytes: function( bytes ) {
        var s = this._data.substr( this._offset, bytes );
        this._offset += bytes;
        return s;
        },

        setByteStream: function( data ) {

            if( typeof data != "string" )
            throw new TypeError( typeof data + " must be string" );

        this._data = data;
        this._offset = 0;
        return this;
        },

        readDouble: function( littleEndian ) {
        var s = this.readBytes( 8 );
        var pow = Math.pow, sign, exponent, fraction;

            if( littleEndian )
            s = s.split("").reverse().join("");

        sign =  ( s.charCodeAt(0) & 0x80 ) >> 7;
        exponent =  ( ( s.charCodeAt(0) & 0x7F ) << 4 ) | ( ( s.charCodeAt(1) & 0xF0 ) >> 4 );
        fraction =  ( ( s.charCodeAt(1) & 0x0F ) * pow(2, 48) ) +
                s.charCodeAt(2) * pow( 2, 40 ) +
                s.charCodeAt(3) * pow( 2, 32 ) +
                ( ( s.charCodeAt(4) & 0xFF ) << 24 ) +
                ( ( s.charCodeAt(5) & 0xFF ) << 16 ) +
                ( ( s.charCodeAt(6) & 0xFF ) << 8  ) +
                s.charCodeAt(7);

        sign = pow( -1, sign );

            if( exponent === 2047 ) {
                if( f !== 0)
                return Number.NaN;

                else if( sign < 0 )
                return -Infinity;

                else
                return Infinity;
            }
            else if( exponent > 0 )
            return sign * Math.pow( 2, exponent - 1023 ) * ( fraction / 0x10000000000000 + 1 );


            else if ( fraction !== 0 )
            return sign * Math.pow( 2, -1022 ) * ( fraction / 0x10000000000000 );


            else 
            return 0;

        },

        readSingle: function( littleEndian ) {
        var s = this.readBytes( 4 )
        var sign, exponent, fraction;

            if( littleEndian )
            s = s.split("").reverse().join("");

        sign =  ( s.charCodeAt(0) & 0x80 ) >> 7;
        exponent =  ( ( s.charCodeAt(0) & 0x7F ) << 1 )  | ( ( s.charCodeAt(1) & 0x80 ) >> 7 );
        fraction =  ( ( s.charCodeAt(1) & 0x7F ) << 16 ) |
                ( ( s.charCodeAt(2) & 0xFF ) << 8 )  |
                ( s.charCodeAt(3) & 0xFF );

        sign = Math.pow( -1, sign );

            if( exponent === 255 ) {

                if( fraction !== 0 )
                return Number.Nan;

                else if( sign < 0 )
                return -Infinity;

                else
                return Infinity;
            }
            else if( exponent > 0 )
            return sign * Math.pow(2, exponent - 127) * ( fraction / 0x800000 + 1 );

            else if ( fraction !== 0 )
            return sign *  Math.pow(2, -126) * ( fraction / 0x800000 );

            else
            return 0;

        },

        readSByte: function() {
        var s = this.readBytes( 1 ).charCodeAt( 0 ) & 0xFF;
        return ( s ^ 0x80 ) - 0x80;
        },

        readUByte: function() {
        return this.readBytes( 1 ).charCodeAt( 0 ) & 0xFF;
        },

        readUShort: function( littleEndian ) {
        var s = this.readBytes( 2 );

            if( littleEndian )
            return ( s.charCodeAt( 0 ) & 0xFF ) |
            ( ( s.charCodeAt( 1 ) & 0xFF) << 8 );

            else
            return ( s.charCodeAt( 1 ) & 0xFF ) |
            ( ( s.charCodeAt( 0 ) & 0xFF) << 8 );
        },

        readULong: function( littleEndian ) {
        var s = this.readBytes( 4 ), r;

            if( littleEndian ) 
            r = ( s.charCodeAt( 0 ) & 0xFF )        |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 3 ) & 0xFF ) << 24 );

            else
            r = ( s.charCodeAt( 3 ) & 0xFF )        |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 0 ) & 0xFF ) << 24 );

            if ( r & 0x80000000 )
            r = ( r & 0x7FFFFFFF ) + 0x80000000;

        return r;
        },

        readSShort: function( littleEndian ){
        var s = this.readBytes( 2 ), r;

            if( littleEndian )
            r = ( s.charCodeAt( 0 ) & 0xFF ) |
            ( ( s.charCodeAt( 1 ) & 0xFF) << 8 );

            else
            r = ( s.charCodeAt( 1 ) & 0xFF ) |
            ( ( s.charCodeAt( 0 ) & 0xFF) << 8 );

        return ( r ^ 0x8000 ) - 0x8000;
        },

        readSLong: function( littleEndian ){
        var s = this.readBytes( 4 ), r;

            if( littleEndian ) 
            return ( s.charCodeAt( 0 ) & 0xFF ) |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 3 ) & 0xFF ) << 24 );

            else
            return ( s.charCodeAt( 3 ) & 0xFF ) |
            ( ( s.charCodeAt( 2 ) & 0xFF ) << 8 )   |
            ( ( s.charCodeAt( 1 ) & 0xFF ) << 16 )  |
            ( ( s.charCodeAt( 0 ) & 0xFF ) << 24 );

        }


    };

Has been tested with .wav files a lot.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文