Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- std::unique_ptr<PixelBuffer> FrameGrabber::GetNextFrame()
- {
- uint32 width = impl->pCodecCtx->width;
- uint32 height = impl->pCodecCtx->height;
- AVFrame* pFrame = avcodec_alloc_frame();
- AVFrame* pRGBFrame = avcodec_alloc_frame();
- int numBytes = avpicture_get_size(PIX_FMT_RGB24, width, height);
- uint8_t* buffer = (uint8_t*)av_malloc(numBytes * sizeof(uint8_t));
- int byteSize = avpicture_fill((AVPicture*)pRGBFrame, buffer, PIX_FMT_RGB24, width, height);
- int frameFinished;
- AVPacket packet;
- auto sws = sws_getContext(width, height, PIX_FMT_YUV420P, width, height, PIX_FMT_RGB24, SWS_BICUBIC, 0, 0, 0);
- while(av_read_frame(impl->pFormatCtx, &packet) >= 0)
- {
- if(packet.stream_index == impl->videoStream)
- {
- avcodec_decode_video2(impl->pCodecCtx, pFrame, &frameFinished, &packet);
- if(frameFinished)
- {
- if(!SanityCheck(pFrame))
- throw std::exception("Bad frame");
- glm::ivec2 size(width, height);
- int err = sws_scale(sws, pFrame->data, pFrame->linesize, 0, height, pRGBFrame->data, pRGBFrame->linesize);
- if(!SanityCheck(pRGBFrame))
- throw std::exception("Bad frame");
- uint8* data = new uint8[byteSize];
- memcpy(data, pRGBFrame->data[0], byteSize);
- auto pixels = std::unique_ptr<PixelBuffer>(new PixelBuffer(size, std::unique_ptr<uint8>(data)));
- sws_freeContext(sws);
- avcodec_free_frame(&pFrame);
- avcodec_free_frame(&pRGBFrame);
- av_free_packet(&packet);
- av_free(buffer);
- return pixels;
- }
- }
- }
- av_free(buffer);
- sws_freeContext(sws);
- avcodec_free_frame(&pFrame);
- avcodec_free_frame(&pRGBFrame);
- av_free_packet(&packet);
- return nullptr;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement