What is the process for introducing a video stream using a WebRTC connection from a different peer?

Currently, I am in the process of learning WebRTC with the goal of creating a basic chat system that includes video call functionality. To achieve this, I have incorporated Django channels to handle the websockets and establish connections between peers. However, an issue has arisen where I am unable to retrieve the media stream from the other peer and display it on the screen.

The connection itself appears to be successful as messages are successfully transmitted via sockets without any errors appearing in the console. Despite this, I am left wondering what exactly I might be overlooking.

The sequence logic is structured as follows:

  • User1 enters the virtual room

  • User2 joins the room

  • User1 sends a message to User2 through the established socket connection

  • User1 initiates a video call by pressing "call" to communicate with User2, access local media, and start the WebRTC connection

  • User2 responds to the call by accepting it, responding with their local media, and establishing the bi-directional communication

Edit 1: A Working Order of Steps:

  • User1 enters the room

  • User1 initiates a call by clicking "call", obtaining local media, and initializing the WebRTC connection

  • User2 enters the room

  • User2 accepts the call by clicking "respond", sharing their local media, and finalizing the connection

  • User1 also clicks "respond"

It's puzzling as to why this specific order seems to work - particularly where "pc.ontrack" appears to only trigger in this precise sequence. Additionally, the ability to commence a WebRTC connection before the second peer joins the room raises questions.

room.html:

<!-- chat/templates/chat/room.html -->
<!DOCTYPE html>
{% load static %}
{% extends 'main/header.html' %}

{% block content %}

<body>

<div class="container">
    <a class="waves-effect waves-light btn prefix" id='call'>call</a>
    <a class="waves-effect waves-light btn prefix" id='respond'>respond</a>
  <div class="copy">Send your URL to a friend to start a video call</div>
  <video id="localVideo" autoplay muted></video>
  <video id="remoteVideo" autoplay></video>
    <textarea id="chat-log"  class="materialize-textarea" ></textarea><br/>

<div class="input-field col s12 ">
    <input id="chat-message-input" type="text" />
    <a class="waves-effect waves-light btn prefix" id="chat-message-submit"><i class="material-icons right">send</i></a>

</div>

</div>

</body>
<script>src = "{% static 'main/js/client.js' %}"></script>
{% endblock  %}

client.js:

// Generate random room name if needed

var roomName = "{{ room_name|escapejs }}";
var drone = new WebSocket(
        'ws://' + window.location.host +
        '/ws/chat/' + roomName + '/');
...

Various events such as sending messages, handling offers, initiating calls, and managing ICE candidates are meticulously detailed within the client.js script.

The console outputs illustrate the interactions between users, the initiation of video calls, and the exchange of media streams as part of the debugging process.

Answer №1

When responding, it is important to act promptly without delay, even before the getUserMedia function and addTracks operation are completed. These tasks run asynchronously and must be completed prior to calling createAnswer. As a result, the response does not include a media stream and the ontrack function will not be triggered on the initiating end.

Utilizing promise syntax can simplify this process, as shown below:

pc.setRemoteDescription(offer)
.then(() => {
  return navigator.mediaDevices.getUserMedia({audio: true, video: true});
})
.then(stream => {
  stream.getTracks().forEach(track => pc.addTrack(track, stream));
  return pc.createAnswer();
})
... then proceed with setLocalDescription and communicate back to the initiator

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

What is the best way to show only one div at a time when selecting from navbar buttons?

To only display the appropriate div when clicking a button on the left navbar and hide all others, you can use this code: For example: If "Profile" is clicked in the left navbar, the My Profile Form div will be displayed (and all others will remain hidde ...

What is the best approach for adding variable rows to a Postgres junction table: should you concatenate a query string, utilize multiple queries, or explore alternative methods

Below is the code snippet for handling a variable-length list of tags and inserting data into the database: // JSON object from req.body { "title": "title", "reference": "1213", "noteType": &q ...

How to retrieve the user ID of the selected user using JqueryUI autocomplete?

Hey there, I'm currently delving into the world of jQuery UI autocomplete. My setup involves using autocomplete with ajax, where PHP helps me fetch a list of users. autocompleteajax.js $(function() { $( "#ranksearch" ).autocomplete({ sou ...

Generate Material UI sidebar components that are positioned above all other components

I am currently working on a sidebar component using the Material UI Drawer component. I am looking to add components that align side by side with the sidebar, similar to the green box shown in the image below. https://i.sstatic.net/aAtn6.png After attem ...

Error message in Linux for NodeJS global NPM package: "File or directory does not exist"

After setting up my Ubuntu 14.04 system, I installed nodejs and npm using the command: sudo apt-get install nodejs npm To ensure packages utilize the node interpreter instead of nodejs, I created a symlink with: sudo ln -s /usr/bin/nodejs /usr/local/bin ...

I possess a pair of arrays, and I aim to transfer certain elements from Array1 to Array2 while maintaining their references

Looking to implement two JavaScript arrays using AngularJS. My goal is to transfer elements from Ar1 to Ar2, and then have any changes made to the values in Ar2 automatically update the values in Ar1 as well. ...

Best practices for securing string values in Node.js

Looking to retrieve the IP address with nodejs/express. Check out the code snippet below that accomplishes this: const ipAddress = String(req.ip || "unknown"); Considering that req.ip is pulled from an HTTP header, there's a potential risk ...

Error: Attempted to access the 'state' property of an undefined object

I am working with the following function: extractCountries: function() { var newLocales = []; _.forEach(this.props.countries, function(locale) { var monthTemp = Utils.thisMonthTemp(parseFloat(locale["name"]["temperature"])); if(p ...

The issue with Bootstrap 4 toggle not correctly hiding the following div

I am trying to hide one div when the other div is displayed using Bootstrap code. However, both divs are currently displaying and my code is not working as intended. If anyone can provide assistance, it would be greatly appreciated. <link rel="st ...

Exporting a VueJS webpage to save as an HTML file on your computer

Scenario: I am working on a project where I need to provide users with the option to download a static export of a webpage that includes VueJS as a JavaScript framework. I attempted to export using filesaver.js and blob with the mimetype text/html, making ...

changing pictures with jquery

Struggling with this code snippet: $('#clicked_package').css({"background-image" : "url(img/head_2.png)"}).fadeOut("slow"); $('#clicked_package').css({"background-image" : "url(img/head_2_normal.png)"}).fadeIn("slow"); No matter which ...

Angular/Karma Unit Test for HttpClient

During my research on unit testing, I came across some very useful examples. Most of the examples focus on unit testing functions that interact with Angular's HttpClient, and they usually look like this: it('should return an Observable<User[] ...

Elevate the value of a particular element's variable through the execution of a function

By using a for loop, I was able to generate a variable number of divs that change their background color individually when hovered over with the mouse. Now, I want to implement a function that will decrease the brightness of each div by 10% every time it i ...

Using Selenium to scroll down to an element until its 'style' changes

I'm in the process of scraping a review page similar to this one. While this specific page has only a few reviews, there are others with a larger volume that require extensive scrolling. Upon observation, I noticed that when the page is not complete ...

How can you access a sibling of the parent element of the current element in Jquery?

I'm working on an HTML project where I have a select field. Depending on the option selected, I need to update the price field with the corresponding price fetched using Ajax. Additionally, I want to be able to input multiple rows by clicking on the ...

Morgan middleware in Express.js specifically targeting unsuccessful requests for logging purposes

Currently, I am facing an issue with my middleware setup in Express.js while using Morgan. The problem arises because Morgan is only logging requests that return error code 302 (redirected), which happens when my middleware encounters an error and redirect ...

Error: The value of "$tweetId" cannot be parsed as it is set to "undefined". Please ensure that string values are properly enclosed

I am utilizing sanity, and if you require more details, I will furnish it promptly. When I try to access http://localhost:3000/api/getComments, I encounter the following error message: ClientError: Unable to process value of "$tweetId=undefined". Kindly ...

The error message "Uncaught (in promise) ReferenceError: dispatch is not defined" indicates that

Currently, I am utilizing vuex with index.js and auth.js stored in the store folder. My goal is to perform a basic sign-in operation within my signin.vue by calling an action from the store. However, I encountered the error 'Uncaught (in promise) Refe ...

Struggling to send the correct array in response to an HTTP request. Is there a way to efficiently send results from a function using expressjs?

Issue Summary: Currently, I am facing a challenge while working on a software program that relies on an SQL database at the backend and utilizes the npm SQLite3 module for communication purposes. The problem arose when performing an HTTP request to the ser ...

Mysterious occurrences always seem to unfold whenever I implement passport for user authentication in my Node.js and Express applications

At first, I wrote the following code snippet to define LocalStrategy: passport.use( 'local-login', new LocalStrategy({ usernameField:'username', passwordField: 'password', passReqtoCallback: tr ...