gpt4 book ai didi

qt - 如何在Qt中通过以太网播放流音频?

转载 作者:行者123 更新时间:2023-12-02 22:09:51 25 4
gpt4 key购买 nike

我的目标是通过LAN网络传输* .wav文件,而不会延迟或使用最少的文件。

另外,我们在服务器计算机上按部分读取文件,两者均为320字节。此后,我们通过UDP发送数据包,并在 jitter buffer 中写入接收信息。 jitter buffer 的大小为10。
我应该在计时器上设置什么延迟以获得清晰的声音?

这是发件人:

void MainWindow::on_start_tx_triggered()
{
timer1 = new QTimer (this);
udpSocketout = new QUdpSocket(this);
qDebug()<<"Start";
for (int i = 0; i < playlist.size(); ++i)
{
inputFile.setFileName(playlist.at(i));
qDebug()<<inputFile.fileName();
if (!inputFile.open(QIODevice::ReadOnly))
{
qDebug()<< "file not found;";
}
}
connect(timer1, SIGNAL(timeout()), this, SLOT(writeDatagrams()));
timer1->start(5);
}

void MainWindow::writeDatagrams()
{
if(!inputFile.atEnd()){
payloadout = inputFile.read(320);
}
qDebug()<<payloadout;
QDataStream out(&datagramout, QIODevice::WriteOnly);
out.setVersion(QDataStream::Qt_4_7);
out << qint64(0);
out << payloadout;
out.device()->seek(qint64(0));
out << qint64(datagramout.size() - sizeof(qint64));
qint64 writtenBytes = udpSocketout->writeDatagram(datagramout, remoteHOST, remotePORT);
qDebug() << "Sent " << writtenBytes << " bytes.";
}

这是接收者和播放器:
void MainWindow::on_start_rx_triggered()
{
udpSocketin = new QUdpSocket(this);
udpSocketin->bind(localHOST, localPORT);
connect(udpSocketin, SIGNAL(readyRead()),
this, SLOT(readDatagrams()));
QDataStream out(&datagramout, QIODevice::WriteOnly);
out.setVersion(QDataStream::Qt_4_7);
timer2 = new QTimer (this);
connect(timer2, SIGNAL(timeout()), this, SLOT(playbuff()));
timer2->start(50);
audioout = new QAudioOutput(format, this);
}

void MainWindow::readDatagrams()
{
datagramin.resize(udpSocketin->pendingDatagramSize());
qint64 receiveBytes = udpSocketin->readDatagram(datagramin.data(), datagramin.size());
qDebug() << "Receive " << receiveBytes << " bytes.";
QDataStream in(&datagramin, QIODevice::ReadOnly);
in.setVersion(QDataStream::Qt_4_7);
quint64 size = 0;
if(in.device()->size() > sizeof(quint64))
{
in >> size;
}
else
return;
if(in.device()->size() < size)
return;
in >> payloadin;
qDebug() << payloadin.size();
emit jitterbuff();
}

void MainWindow::jitterbuff()
{
if (buff_pos < SIZE_OF_BUF)
{
QDataStream out(&buffered, QIODevice::WriteOnly);
out.setVersion(QDataStream::Qt_4_7);
out << payloadin;
buff_pos++;
}
else
buff_pos = 0;
}

void MainWindow::playbuff()
{
qDebug() << "YES!!!";
buffer = new QBuffer(&buffered);
buffer->open(QIODevice::ReadOnly);
audioout->start(buffer);
QEventLoop loop;
QTimer::singleShot(50, &loop, SLOT(quit()));
loop.exec();
buffer->close();
}

最佳答案

这个问题解决了。 QAdioOutput有两种模式;有“推”和“拉”。我提供了一个指向QIODevice的指针,并将数据直接写入该指针。解决方案:

读取UDP套接字:

void MainWindow::on_start_rx_triggered()
{
udpSocketin = new QUdpSocket(this);
udpSocketin->bind(localPORT);
connect(udpSocketin, SIGNAL(readyRead()), this, SLOT(readDatagrams()));
QDataStream out(&datagramout, QIODevice::WriteOnly);
out.setVersion(QDataStream::Qt_4_7);
timer2 = new QTimer (this);
connect(timer2, SIGNAL(timeout()), this, SLOT(playbuff()));
timer2->setInterval(15*9);
audioout = new QAudioOutput(format, this);
input = audioout->start();
}

void MainWindow::readDatagrams()
{
if (udpSocketin->hasPendingDatagrams()){
datagramin.resize(udpSocketin->pendingDatagramSize());
qint64 receiveBytes = udpSocketin->readDatagram(datagramin.data(), datagramin.size());
if (receiveBytes <= 0)
{
msg.warning(this, "File ERROR", "The end!", QMessageBox::Ok);
emit on_stop_rx_triggered();
}
QDataStream in(&datagramin, QIODevice::ReadOnly);
in.setVersion(QDataStream::Qt_4_7);
quint64 size = 0;
if(in.device()->size() > sizeof(quint64))
{
in >> size;
}
else return;
in >> rxfilename;
in >> name;
in >> payloadin;
emit jitterbuff();
}

void MainWindow::jitterbuff()
{
if (buff_pos < SIZE_OF_BUF)
{
buffered.append(payloadin);
buff_pos++;
}
else
{
timer2->start();
buffered.clear();
buff_pos = 0;
}
}

void MainWindow::playbuff()
{
if (!buffered.isEmpty())
{
buffer = new QBuffer(&buffered);
buffer->open(QIODevice::ReadOnly);
input->write(buffered);
buffer->close();
}
}

写入UDP套接字:
void MainWindow::on_start_tx_triggered()
{
timer1 = new QTimer (this);
udpSocketout = new QUdpSocket(this);
inputFile.setFileName(playlist.at(playIDfile));
if (!inputFile.open(QIODevice::ReadOnly))
{
msg.warning(this, "File ERROR", "File not found!", QMessageBox::Ok);
return;
}
fileinfo = new QFileInfo (inputFile);
txfilename = fileinfo->fileName();
ui->playedFile->setText("Now played: " + txfilename);
connect(timer1, SIGNAL(timeout()), this, SLOT(writeDatagrams()));
timer1->start(15);
}
void MainWindow::writeDatagrams()
{

if(!inputFile.atEnd()){
payloadout = inputFile.read(SIZE_OF_SOUND);
QDataStream out(&datagramout, QIODevice::WriteOnly);
out.setVersion(QDataStream::Qt_4_7);
out << qint64(0);
out << txfilename;
out << name;
out << payloadout;
out.device()->seek(qint64(0));
out << qint64(datagramout.size() - sizeof(qint64));
qint64 writtenBytes = udpSocketout->writeDatagram(datagramout, remoteHOST, remotePORT);
}
}

如果有人有问题,我会尽力帮助他/她。

关于qt - 如何在Qt中通过以太网播放流音频?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10692333/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com