Giter VIP home page Giter VIP logo

Comments (5)

muaz-khan avatar muaz-khan commented on June 1, 2024

Need to use x-google-min-bitrate and x-google-max-bitrate:

a=fmtp:111 x-google-min-bitrate=50; x-google-max-bitrate=50

You can inject these lines using processSdp method:

connection.processSdp = function(sdp) {
    sdp = sdp.replace(/a=mid:audio\r\n/g, 'a=mid:audio\r\na=fmtp:111 x-google-min-bitrate=50; x-google-max-bitrate=50\r\n');
    return sdp;
};

I didn't test above snippet however you may need to do a little bit modifications to use exact opus codec number instead of 111. Such numbers can be taken using m=audio (\d+) RTP/SAVPF

Updated

connection.processSdp = function (sdp) {
    sdp = addStereo(sdp);
    return sdp;
};

function addStereo(sdp) {
    var sdpLines = sdp.split('\r\n');

    // Find opus payload.
    var opusIndex = findLine(sdpLines, 'a=rtpmap', 'opus/48000');
    var opusPayload;
    if (opusIndex) {
        opusPayload = getCodecPayloadType(sdpLines[opusIndex]);
    }

    // Find the payload in fmtp line.
    var fmtpLineIndex = findLine(sdpLines, 'a=fmtp:' + opusPayload.toString());
    if (fmtpLineIndex === null) {
        return sdp;
    }

    // Append stereo=1 to fmtp line.
    // added maxaveragebitrate here; about 50 kbits/s
    // added stereo=1 here for stereo audio
    // x-google-min-bitrate=50; x-google-max-bitrate=50
    sdpLines[fmtpLineIndex] = sdpLines[fmtpLineIndex].concat('; stereo=1; maxaveragebitrate=' + (50 * 1024) + '; x-google-min-bitrate=50; x-google-max-bitrate=50');

    sdp = sdpLines.join('\r\n');
    return sdp;
}

// Find the line in sdpLines that starts with |prefix|, and, if specified,
// contains |substr| (case-insensitive search).
function findLine(sdpLines, prefix, substr) {
    return findLineInRange(sdpLines, 0, -1, prefix, substr);
}

// Find the line in sdpLines[startLine...endLine - 1] that starts with |prefix|
// and, if specified, contains |substr| (case-insensitive search).
function findLineInRange(sdpLines, startLine, endLine, prefix, substr) {
    var realEndLine = endLine !== -1 ? endLine : sdpLines.length;
    for (var i = startLine; i < realEndLine; ++i) {
        if (sdpLines[i].indexOf(prefix) === 0) {
            if (!substr ||
                sdpLines[i].toLowerCase().indexOf(substr.toLowerCase()) !== -1) {
                return i;
            }
        }
    }
    return null;
}

// Gets the codec payload type from an a=rtpmap:X line.
function getCodecPayloadType(sdpLine) {
    var pattern = new RegExp('a=rtpmap:(\\d+) \\w+\\/\\d+');
    var result = sdpLine.match(pattern);
    return (result && result.length === 2) ? result[1] : null;
}

from rtcmulticonnection.

lepinsk avatar lepinsk commented on June 1, 2024

Thanks for the info – unfortunately it doesn't seem like these are changing anything.

Here's a copy of the SDP from my session:

type: offer, sdp: v=0
o=- 4997007992604132131 2 IN IP4 127.0.0.1
s=-
t=0 0
a=group:BUNDLE audio data
a=msid-semantic: WMS fbd58a6f-b41b-4d74-88f9-7742b3a1e48f
m=audio 1 RTP/SAVPF 111 103 104 0 8 106 105 13 126
c=IN IP4 0.0.0.0
a=rtcp:1 IN IP4 0.0.0.0
a=ice-ufrag:K0tzbZhFjBgQdRz2
a=ice-pwd:cWXnc2ZTO0Z8QpRub9PMJWd9
a=ice-options:google-ice
a=fingerprint:sha-256 11:7B:5B:B2:0D:A5:D1:2D:56:56:9C:5F:06:61:89:C5:59:18:A0:5F:A4:4E:94:53:4A:DF:D0:34:0B:CB:ED:E2
a=setup:actpass
a=mid:audio
a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level
a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
a=sendrecv
a=rtcp-mux
a=rtpmap:111 opus/48000/2
a=fmtp:111 minptime=10; stereo=1; maxaveragebitrate=51200; x-google-min-bitrate=50; x-google-max-bitrate=50;
a=rtpmap:103 ISAC/16000
a=rtpmap:104 ISAC/32000
a=rtpmap:0 PCMU/8000
a=rtpmap:8 PCMA/8000
a=rtpmap:106 CN/32000
a=rtpmap:105 CN/16000
a=rtpmap:13 CN/8000
a=rtpmap:126 telephone-event/8000
a=maxptime:60
a=ssrc:2541565870 cname:CQXZOuXLXOTMTnMB
a=ssrc:2541565870 msid:fbd58a6f-b41b-4d74-88f9-7742b3a1e48f 3c555a22-2f3c-4732-be6d-e4004dc112fa
a=ssrc:2541565870 mslabel:fbd58a6f-b41b-4d74-88f9-7742b3a1e48f
a=ssrc:2541565870 label:3c555a22-2f3c-4732-be6d-e4004dc112fa
m=application 1 RTP/SAVPF 101
c=IN IP4 0.0.0.0
a=rtcp:1 IN IP4 0.0.0.0
a=ice-ufrag:K0tzbZhFjBgQdRz2
a=ice-pwd:cWXnc2ZTO0Z8QpRub9PMJWd9
a=ice-options:google-ice
a=fingerprint:sha-256 11:7B:5B:B2:0D:A5:D1:2D:56:56:9C:5F:06:61:89:C5:59:18:A0:5F:A4:4E:94:53:4A:DF:D0:34:0B:CB:ED:E2
a=setup:actpass
a=mid:data
a=sendrecv
a=rtcp-mux
a=rtpmap:101 google-data/90000
a=ssrc:1535520575 cname:VkmXkzBkUkiyPsTD
a=ssrc:1535520575 msid:data-channel data-channel
a=ssrc:1535520575 mslabel:data-channel
a=ssrc:1535520575 label:data-channel

And my audio bandwidth graph:
screen shot 2014-12-10 at 3 34 38 pm

from rtcmulticonnection.

muaz-khan avatar muaz-khan commented on June 1, 2024
connection.processSdp = function(sdp) {
    return addVideoBandwidth(sdp);
};

function addVideoBandwidth(sdp) {
    var sdpLines = sdp.split('\r\n');

    var vp8Index = findLine(sdpLines, 'a=rtpmap', 'VP8/90000');
    var vp8Payload;
    if (vp8Index) {
        vp8Payload = getCodecPayloadType(sdpLines[vp8Index]);
    }

    var rtxIndex = findLine(sdpLines, 'a=rtpmap', 'rtx/90000');
    var rtxPayload;
    if (rtxIndex) {
        rtxPayload = getCodecPayloadType(sdpLines[rtxIndex]);
    }

    var rtxFmtpLineIndex = findLine(sdpLines, 'a=fmtp:' + rtxPayload.toString());
    if (rtxFmtpLineIndex !== null) {
        var appendrtxNext = '\r\n';
        appendrtxNext += 'a=fmtp:' + vp8Payload + ' x-google-min-bitrate=228; x-google-max-bitrate=228';
        sdpLines[rtxFmtpLineIndex] = sdpLines[rtxFmtpLineIndex].concat(appendrtxNext);
        sdp = sdpLines.join('\r\n');
    }

    return sdp;
}

function findLine(sdpLines, prefix, substr) {
    return findLineInRange(sdpLines, 0, -1, prefix, substr);
}

function findLineInRange(sdpLines, startLine, endLine, prefix, substr) {
    var realEndLine = endLine !== -1 ? endLine : sdpLines.length;
    for (var i = startLine; i < realEndLine; ++i) {
        if (sdpLines[i].indexOf(prefix) === 0) {
            if (!substr ||
                sdpLines[i].toLowerCase().indexOf(substr.toLowerCase()) !== -1) {
                return i;
            }
        }
    }
    return null;
}

function getCodecPayloadType(sdpLine) {
    var pattern = new RegExp('a=rtpmap:(\\d+) \\w+\\/\\d+');
    var result = sdpLine.match(pattern);
    return (result && result.length === 2) ? result[1] : null;
}

from rtcmulticonnection.

lepinsk avatar lepinsk commented on June 1, 2024

Hey Muaz,

Thanks for the ongoing help with this. I wonder if it's possible that I'm reading these graphs wrong?

I'm trying out your Custom Bandwidth example here: https://www.webrtc-experiment.com/RTCMultiConnection/bandwidth.html?audio=30&video=30

I can see the b=AS:30 lines in the local and remote SDP descriptions, but it seems like I'm seeing conflicting information in my bandwidth graphs.

stats graphs for Conn-audio-1-0 shows both bitsSentPerSecond and bitsReceivedPerSecond locked to just under 80kbps:
screen shot 2014-12-29 at 3 54 32 pm

Shouldn't I be seeing those values around 30kbps? I've noticed that when I expand the various SSRCs (such as Stats graphs for ssrc_476401739_send), their bandwidth levels are closer to 30kbps sending and receiving:
screen shot 2014-12-29 at 3 59 48 pm

Is it possible that I'm misreading the data on this page and I shouldn't be reading Conn-audio-1-0?

from rtcmulticonnection.

manueltato11 avatar manueltato11 commented on June 1, 2024

Hello,

Very interesting to see WebRTC consumption, as I can prove or to remove these graphics,

Thank you,

from rtcmulticonnection.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.