void CCVideoThread::run_video() { DPTR_D(CCVideoThread); if (!d.dec || !d.dec->is_available() || !d.writer) return; reset_state(); Q_ASSERT(d.clock != 0); CCDecodeVideo *dec = static_cast<CCDecodeVideo*>(d.dec); CCVideoRenderer* vo = static_cast<CCVideoRenderer*>(d.writer); while (!d.stop) { if (try_pause()) { if (d.stop) break; } std::unique_lock<std::mutex> lock(d.mutex_); if (d.packets.is_empty() && !d.stop) { d.stop = d.demux_end; if (d.stop) { break; } } PacketData pkt; d.packets.pop(pkt); if (!pkt.is_valid()) { qDebug("Invalid pts or empty packet!"); dec->flush_codec(); continue; } d.delay = pkt.pts - d.clock->value(); if (qAbs(d.delay) < 2.718) { if (d.delay > kSyncThreshold) { av_usleep(d.delay * 1000000); } else if (d.delay < -kSyncThreshold) { //continue; } } else { qDebug("delay %f/%f", d.delay, d.clock->value()); if (d.delay > 0) { av_usleep(0.064 * 1000000); } else { continue; } } d.clock->update_video_pts(pkt.pts); bool vo_ok = vo && vo->is_available(); if (vo_ok) { if (vo->last_width() > 0 && vo->last_height() > 0 && !vo->scale_in()) dec->resize_video(vo->last_size()); else vo->set_source_size(dec->width(), dec->height()); //setLastSize() } ByteArray da(pkt.date); if (d.dec->decode(da)) { d.pts = pkt.pts; d.decoded_datas = d.dec->data_video(); if (vo_ok) { vo->write_data(d.decoded_datas); } /*d.width = dec->width(); d.height = dec->height(); d.decoded_datas = d.dec->data_video(); if (vo && vo->is_available()) { vo->set_source_size(dec->width(), dec->height()); vo->write_data(d.decoded_datas); }*/ } if (vo_ok && !vo->scale_in()) vo->set_source_size(vo->video_sizes()); } qDebug("Video thread stops running..."); }