stakwork / sphinx-tribes

Backend for sphinx tribes and bounties. The bounty platform pays out in bitcoin. Sign up with Sphinx Chat, complete a bounty, and earn bitcoin! Go to our website for available bounties.
https://community.sphinx.chat/bounties
32 stars 62 forks source link

[Review] - Real-time data stream from Jitsi Recording #1659

Open tomsmith8 opened 1 month ago

tomsmith8 commented 1 month ago
const domain = "your.jitsi.instance"; // Replace with our Jitsi instance domain
const options = {
    roomName: "exampleRoom",
    width: 700,
    height: 700,
    parentNode: document.querySelector('#meet')
};

const api = new JitsiMeetExternalAPI(domain, options);
let mediaRecorder;
let recordedChunks = [];

api.addEventListener('videoConferenceJoined', () => {
    console.log("Video conference joined");
    document.getElementById('startRecording').addEventListener('click', startRecording);
    document.getElementById('stopRecording').addEventListener('click', stopRecording);
});

function startRecording() {
    navigator.mediaDevices.getUserMedia({ video: true, audio: true })
        .then(userStream => {
            navigator.mediaDevices.getDisplayMedia({ video: true })
                .then(screenStream => {
                    const combinedStream = new MediaStream([...userStream.getTracks(), ...screenStream.getTracks()]);

                    mediaRecorder = new MediaRecorder(combinedStream, { mimeType: 'video/webm; codecs=vp9' });

                    mediaRecorder.ondataavailable = handleDataAvailable;
                    mediaRecorder.onstop = handleStop;

                    mediaRecorder.start();
                    console.log("Recording started");

                    document.getElementById('startRecording').disabled = true;
                    document.getElementById('stopRecording').disabled = false;

                    // Process streams
                    processStreams(combinedStream);
                })
                .catch(error => {
                    console.error('Error accessing display media.', error);
                });
        })
        .catch(error => {
            console.error('Error accessing user media.', error);
        });
}

function stopRecording() {
    mediaRecorder.stop();
    console.log("Recording stopped");

    document.getElementById('startRecording').disabled = false;
    document.getElementById('stopRecording').disabled = true;
}

function handleDataAvailable(event) {
    if (event.data.size > 0) {
        recordedChunks.push(event.data);
    }
}

function handleStop() {
    const blob = new Blob(recordedChunks, {
        type: 'video/webm'
    });
    const url = URL.createObjectURL(blob);
    const a = document.createElement('a');
    a.style.display = 'none';
    a.href = url;
    a.download = 'recording.webm';
    document.body.appendChild(a);
    a.click();
    window.URL.revokeObjectURL(url);
}

function processStreams(stream) {
    stream.getVideoTracks().forEach(track => {
        processVideoTrack(track);
    });

    stream.getAudioTracks().forEach(track => {
        processAudioTrack(track);
    });
}

function processVideoTrack(videoTrack) {
    const videoElement = document.createElement('video');
    videoElement.autoplay = true;
    videoElement.srcObject = new MediaStream([videoTrack]);

    // Add video element to the DOM or process it as needed
    document.body.appendChild(videoElement);

    // Capture frames from the video element
    captureFrame(videoElement);
}

function processAudioTrack(audioTrack) {
    const audioElement = document.createElement('audio');
    audioElement.autoplay = true;
    audioElement.srcObject = new MediaStream([audioTrack]);

    // Add audio element to the DOM or process it as needed
    document.body.appendChild(audioElement);

    // Process audio for speech recognition
    processAudioStream(audioElement.srcObject);
}

function captureFrame(videoElement) {
    const canvas = document.createElement('canvas');
    canvas.width = videoElement.videoWidth;
    canvas.height = videoElement.videoHeight;
    const context = canvas.getContext('2d');

    function drawFrame() {
        context.drawImage(videoElement, 0, 0, canvas.width, canvas.height);
        const frame = canvas.toDataURL('image/png');

        // Send frame to external API
        sendFrameToAPI(frame);

        requestAnimationFrame(drawFrame);
    }

    drawFrame();
}

function sendFrameToAPI(frame) {
    fetch('https://example.com/api/frames', { // Replace with stakwork external API URL
        method: 'POST',
        headers: {
            'Content-Type': 'application/json'
        },
        body: JSON.stringify({ image: frame })
    })
    .then(response => response.json())
    .then(data => console.log('Frame sent successfully:', data))
    .catch(error => console.error('Error sending frame:', error));
}

function processAudioStream(audioStream) {
    const audioContext = new (window.AudioContext || window.webkitAudioContext)();
    const mediaStreamSource = audioContext.createMediaStreamSource(audioStream);
    const processor = audioContext.createScriptProcessor(4096, 1, 1);

    mediaStreamSource.connect(processor);
    processor.connect(audioContext.destination);

    processor.onaudioprocess = function(event) {
        const audioData = event.inputBuffer.getChannelData(0);

        // Convert Float32Array to Array for JSON serialization
        const audioArray = Array.from(audioData);

        // Send audio data to external API
        sendAudioToAPI(audioArray);
    };
}

function sendAudioToAPI(audioData) {
    fetch('https://example.com/api/audio', { // Replace with stakwork external API URL
        method: 'POST',
        headers: {
            'Content-Type': 'application/json'
        },
        body: JSON.stringify({ audio: audioData })
    })
    .then(response => response.json())
    .then(data => console.log('Audio sent successfully:', data))
    .catch(error => console.error('Error sending audio:', error));
}
aliraza556 commented 1 month ago

@tomsmith8 please assign me