public extern static void CallResulOfFunction(int a, int b, CBFunction callback);
public static extern void DFCSetCallBack(int channelID, CBFunction func);
public VideoStreamDecoder(string url, bool forceTCP = false, int tcpTimeout = 100, CBFunction callBack = null) { _pFormatContext = ffmpeg.avformat_alloc_context(); var pFormatContext = _pFormatContext; AVDictionary *dic = null; pFormatContext->max_delay = 0; ///https://ffmpeg.org/ffmpeg-protocols.html if (forceTCP) { ffmpeg.av_dict_set(&dic, "rtsp_transport", "tcp", 0); ffmpeg.av_dict_set(&dic, "stimeout", $"{tcpTimeout}", 0); } else { pFormatContext->max_delay = 0; } if (callBack != null) { _pFormatContext->interrupt_callback = new AVIOInterruptCB() { callback = new AVIOInterruptCB_callback_func() { Pointer = Marshal.GetFunctionPointerForDelegate(callBack) }, opaque = pFormatContext } } ; ffmpeg.avformat_open_input(&pFormatContext, url, null, &dic).ThrowExceptionIfError(); ffmpeg.avformat_find_stream_info(_pFormatContext, null).ThrowExceptionIfError(); // find the first video stream AVStream *pStream = null; for (var i = 0; i < _pFormatContext->nb_streams; i++) { if (_pFormatContext->streams[i]->codec->codec_type == AVMediaType.AVMEDIA_TYPE_VIDEO) { pStream = _pFormatContext->streams[i]; break; } } if (pStream == null) { throw new InvalidOperationException("Could not found video stream."); } _streamIndex = pStream->index; _pCodecContext = pStream->codec; var codecId = _pCodecContext->codec_id; var pCodec = ffmpeg.avcodec_find_decoder(codecId); if (pCodec == null) { throw new InvalidOperationException("Unsupported codec."); } ffmpeg.avcodec_open2(_pCodecContext, pCodec, &dic).ThrowExceptionIfError(); CodecName = ffmpeg.avcodec_get_name(codecId); FrameSize = new Size(_pCodecContext->width, _pCodecContext->height); PixelFormat = _pCodecContext->pix_fmt; _pPacket = ffmpeg.av_packet_alloc(); _pFrame = ffmpeg.av_frame_alloc(); }