# all files / node-opus/lib/ Decoder.js

97.56% Statements 40/41
75% Branches 9/12
100% Functions 4/4
97.56% Lines 40/41

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    1×
    1×
    1×

    1×

    1×
    32×

    32×
    32×
    32×

    32×

    32×
    32×
    32×
    32×

    32×

    1×

    1×

    1700×
    32×
    1668×

    32×

    1636×

    1700×

    1×

    32×

    32×
    32×

    32×
    32×
    32×
    32×
    32×
    32×

    32×

    32×

    1×

    1636×

    1636×
    1636×

    1×

    var util = require( 'util' );
    var Transform = require( 'stream' ).Transform;
    var ogg_packet = require( 'ogg-packet' );

    var OpusEncoder = require( './OpusEncoder' );

    var Decoder = function( rate, channels, frameSize ) {
        Transform.call( this, { readableObjectMode: true } );

        this.rate = rate || 48000;
        this.channels = channels || 1;
        this.frameSize = frameSize || this.rate * 0.04;

        this.encoder = null;

    	this.header = {};
    	this.tags = null;
        this.pos = 0;
        this.samplesWritten = 0;

    	this.packetBuffer = [];
    };
    util.inherits( Decoder, Transform );

    /**
     * Transform stream callback
     */
    Decoder.prototype._transform = function( packet, encoding, done ) {

    	// Write the header if it hasn't been written yet
        if( !this.encoder ) {
    		this._parseHeader( packet );
        } else if( !this.tags ) {
    		// TODO: Not implemented
    		// this._parseTags( packet );
    		this.tags = {};
    	} else {
    		this._processInput( packet );
    	}

        done();
    };

    Decoder.prototype._parseHeader = function( packet ) {

    	var header = packet.packet;

    	var signature = header.slice( 0, 8 );
    	Iif( signature.toString( 'ascii' ) !== 'OpusHead' ) {
    		return this.emit( 'error', 'Bad header' );
    	}

    	this.header.version = header.readUInt8( 8 );
    	this.header.channels = header.readUInt8( 9 );
    	this.header.preSkip = header.readUInt16LE( 10 );
    	this.header.rate = header.readUInt32LE( 12 );
    	this.header.gain = header.readUInt16LE( 16 );
    	this.header.channelMap = header.readUInt8( 18 );

    	this.emit( 'format', {
            channels: this.channels,
            sampleRate: this.rate,
            bitDepth: 16,
            float: false,
            signed: true,

            gain: this.header.gain,
            preSkip: this.header.preSkip,
            version: this.header.version
        });

    	this.encoder = new OpusEncoder( this.rate, this.channels );
    };

    Decoder.prototype._processInput = function( packet ) {

    	var frame = packet.packet;

    	var pcm = this.encoder.decode( frame );
    	this.push( pcm );
    };

    module.exports = Decoder;